Skip to content

Commit c01c652

Browse files
Merge origin/main (Release 1.3.0) into dnsplugins
Brings in upstream fixes from main while preserving the dnsplugins branch architecture (inline DNS providers removed in favor of external plugins resolved via IDomainValidatorFactory). Resolutions: - Kept deletion of inline Cloudflare/Google/Factory providers (moved to plugin projects on this branch). - Dropped provider-specific config fields/annotations re-added by main; those configs now belong to each DNS plugin. - Added main's new Enabled disable-switch: cached AcmeClientConfig in Initialize, early-return in Initialize, and FAILED enrollment when the connector is disabled. - Added main's DnsVerificationServer config (with annotation) for private DNS zones, and wired it into the DnsVerificationHelper constructor call in Enroll. - Kept dnsplugins' AcmeCaPlugin.csproj state (newer IAnyCAPlugin prerelease, Google package removed, other provider packages pending cleanup). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2 parents 9db8bbb + af8add5 commit c01c652

8 files changed

Lines changed: 72 additions & 9 deletions

File tree

.gitignore

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -329,8 +329,8 @@ ASALocalRun/
329329
# MFractors (Xamarin productivity tool) working folder
330330
.mfractor/
331331
/.claude
332-
/MIGRATION-SUMMARY.md
333-
/PLUGIN-MIGRATION-GUIDE.md
334-
/ReflectFramework.csx
335-
/InspectFramework/InspectFramework.csproj
336-
/InspectFramework/Program.cs
332+
MIGRATION-SUMMARY.md
333+
PLUGIN-MIGRATION-GUIDE.md
334+
ReflectFramework.csx
335+
InspectFramework/InspectFramework.csproj
336+
InspectFramework/Program.cs

AcmeCaPlugin/AcmeCaPlugin.cs

Lines changed: 35 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,7 @@ public class AcmeCaPlugin : IAnyCAPlugin
6363
private static readonly ILogger _logger = LogHandler.GetClassLogger<AcmeCaPlugin>();
6464
private IAnyCAPluginConfigProvider Config { get; set; }
6565
private readonly IDomainValidatorFactory _validatorFactory;
66+
private AcmeClientConfig _config;
6667

6768
// Constants for better maintainability
6869
private const string DEFAULT_PRODUCT_ID = "default";
@@ -88,6 +89,16 @@ public void Initialize(IAnyCAPluginConfigProvider configProvider, ICertificateDa
8889
_logger.MethodEntry();
8990
Config = configProvider ?? throw new ArgumentNullException(nameof(configProvider));
9091

92+
_config = GetConfig();
93+
_logger.LogTrace("Enabled: {Enabled}", _config.Enabled);
94+
95+
if (!_config.Enabled)
96+
{
97+
_logger.LogWarning("The CA is currently in the Disabled state. It must be Enabled to perform operations. Skipping config validation...");
98+
_logger.MethodExit();
99+
return;
100+
}
101+
91102
// Validate that factory is available - validators will be resolved per-domain during enrollment
92103
if (_validatorFactory == null)
93104
{
@@ -124,6 +135,12 @@ public DomainValidatorConfigProvider(Dictionary<string, object> config)
124135
public async Task Ping()
125136
{
126137
_logger.MethodEntry();
138+
if (!_config.Enabled)
139+
{
140+
_logger.LogWarning("The CA is currently in the Disabled state. It must be Enabled to perform operations. Skipping connectivity test...");
141+
_logger.MethodExit();
142+
return;
143+
}
127144

128145
HttpClient httpClient = null;
129146
try
@@ -201,6 +218,13 @@ public Task ValidateCAConnectionInfo(Dictionary<string, object> connectionInfo)
201218
var rawData = JsonConvert.SerializeObject(connectionInfo);
202219
var config = JsonConvert.DeserializeObject<AcmeClientConfig>(rawData);
203220

221+
if (config != null && !config.Enabled)
222+
{
223+
_logger.LogWarning("The CA is currently in the Disabled state. It must be Enabled to perform operations. Skipping config validation...");
224+
_logger.MethodExit();
225+
return Task.CompletedTask;
226+
}
227+
204228
// Validate required configuration fields
205229
var missingFields = new List<string>();
206230
if (string.IsNullOrWhiteSpace(config?.DirectoryUrl))
@@ -266,6 +290,16 @@ public async Task<EnrollmentResult> Enroll(
266290
{
267291
_logger.MethodEntry();
268292

293+
if (!_config.Enabled)
294+
{
295+
_logger.LogWarning("The CA is currently in the Disabled state. It must be Enabled to perform operations. Enrollment rejected.");
296+
_logger.MethodExit();
297+
return new EnrollmentResult
298+
{
299+
Status = (int)EndEntityStatus.FAILED,
300+
StatusMessage = "CA connector is disabled. Enable it in the CA configuration to perform enrollments."
301+
};
302+
}
269303

270304
if (string.IsNullOrWhiteSpace(csr))
271305
throw new ArgumentException("CSR cannot be null or empty", nameof(csr));
@@ -500,7 +534,7 @@ private async Task ProcessAuthorizations(AcmeClient acmeClient, OrderDetails ord
500534
throw new InvalidOperationException("Missing or invalid authorization list in order payload.");
501535
}
502536

503-
var dnsVerifier = new DnsVerificationHelper(_logger);
537+
var dnsVerifier = new DnsVerificationHelper(_logger, config.DnsVerificationServer);
504538
var pendingChallenges = new List<(Authorization authz, Challenge challenge, Dns01ChallengeValidationDetails validation, IDomainValidator validator)>();
505539

506540
// First pass: Create all DNS records using per-domain IDomainValidator

AcmeCaPlugin/AcmeCaPlugin.csproj

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
<ImplicitUsings>disable</ImplicitUsings>
55
<Nullable>disable</Nullable>
66
<CopyLocalLockFileAssemblies>true</CopyLocalLockFileAssemblies>
7-
<GenerateAssemblyInfo>false</GenerateAssemblyInfo>
7+
<GenerateAssemblyInfo>true</GenerateAssemblyInfo>
88
<RootNamespace>Keyfactor.Extensions.CAPlugin.Acme</RootNamespace>
99
<AssemblyName>AcmeCaPlugin</AssemblyName>
1010
</PropertyGroup>

AcmeCaPlugin/AcmeCaPluginConfig.cs

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
using Keyfactor.AnyGateway.Extensions;
1+
using Keyfactor.AnyGateway.Extensions;
22
using System.Collections.Generic;
33

44
namespace Keyfactor.Extensions.CAPlugin.Acme
@@ -9,6 +9,13 @@ public static Dictionary<string, PropertyConfigInfo> GetPluginAnnotations()
99
{
1010
return new Dictionary<string, PropertyConfigInfo>()
1111
{
12+
["Enabled"] = new PropertyConfigInfo()
13+
{
14+
Comments = "Enable or disable this CA connector. When disabled, all operations (ping, enroll, sync) are skipped.",
15+
Hidden = false,
16+
DefaultValue = "true",
17+
Type = "Bool"
18+
},
1219
["DirectoryUrl"] = new PropertyConfigInfo()
1320
{
1421
Comments = "ACME directory URL (e.g. Let's Encrypt, ZeroSSL, etc.)",
@@ -60,6 +67,15 @@ public static Dictionary<string, PropertyConfigInfo> GetPluginAnnotations()
6067
Hidden = false,
6168
DefaultValue = "60",
6269
Type = "Number"
70+
},
71+
72+
// DNS Verification Settings
73+
["DnsVerificationServer"] = new PropertyConfigInfo()
74+
{
75+
Comments = "DNS server to use for verifying TXT record propagation. For private/local DNS zones, set this to your authoritative DNS server IP (e.g., 10.3.10.37). Leave empty to use public DNS servers (Google, Cloudflare, etc.).",
76+
Hidden = false,
77+
DefaultValue = "",
78+
Type = "String"
6379
}
6480

6581
};

AcmeCaPlugin/AcmeClientConfig.cs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
{
33
public class AcmeClientConfig
44
{
5+
public bool Enabled { get; set; } = true;
56
public string DirectoryUrl { get; set; } = "https://acme-v02.api.letsencrypt.org/directory";
67
public string Email { get; set; } = string.Empty;
78
public string EabKid { get; set; } = null;
@@ -14,5 +15,8 @@ public class AcmeClientConfig
1415
// DNS Propagation Delay (in seconds) - wait this long after creating DNS records before checking propagation
1516
public int DnsPropagationDelaySeconds { get; set; } = 60;
1617

18+
// DNS Verification Settings - DNS server IP for verification (for private zones)
19+
public string DnsVerificationServer { get; set; } = null;
20+
1721
}
1822
}

CHANGELOG.md

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
# v1.2.0
1+
# v1.3.0
2+
* Containerization Changes for SaaS Environment
3+
* Fixed URL CaId Length issue
4+
5+
# v1.2.0
26
* Added RFC 2136 Dynamic DNS Provider Support (BIND with TSIG authentication)
37
* Added Infoblox DNS Provider Support
48
* Added configurable DNS verification server for private/local DNS zones

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -674,6 +674,7 @@ spec:
674674

675675
Populate using the configuration fields collected in the [requirements](#requirements) section.
676676

677+
* **Enabled** - Enable or disable this CA connector. When disabled, all operations (ping, enroll, sync) are skipped.
677678
* **DirectoryUrl** - ACME directory URL (e.g. Let's Encrypt, ZeroSSL, etc.)
678679
* **Email** - Email for ACME account registration.
679680
* **EabKid** - External Account Binding Key ID (optional)

integration-manifest.json

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,10 @@
1313
"about": {
1414
"carest": {
1515
"ca_plugin_config": [
16+
{
17+
"name": "Enabled",
18+
"description": "Enable or disable this CA connector. When disabled, all operations (ping, enroll, sync) are skipped."
19+
},
1620
{
1721
"name": "DirectoryUrl",
1822
"description": "ACME directory URL (e.g. Let's Encrypt, ZeroSSL, etc.)"

0 commit comments

Comments
 (0)