Skip to content

Conversation

Borgquite
Copy link
Contributor

@Borgquite Borgquite commented Oct 2, 2025

Pull Request (PR) description

A few bugs discovered when I tried to add an RODC using a pre-staged account. This should fix them:

  • ADDomainController was checking to see if a DC object for the current computer existed to determine if the resource needed to run or not. For RODCs with a pre-staged accounts, this always exists prior to promotion. Added logic that checks to see if the operating system thinks it is a DC or not, which runs before trying to obtain the AD DC object.
  • This replicated some logic in the common function Get-DomainControllerObject (which is also used by ADReadOnlyDomainControllerAccount, but in that function, this check is not required) so removed it there to make the function more generic.
  • Added a Read Only parameter 'Enabled' to ADReadOnlyDomainControllerAccount allowing it to be checked whether it is pre-staged but not yet used (Disabled / Unoccupied) or in use (Enabled).
  • Can't use certain parameters with UseExistingAccount - don't have time to write checks in the code, but have put some comments in the parameter descriptions instead for now.
  • CodeRabbit asked me to add a few $null object guards, and fix some documentation on used functions at the same time.

All seems to work OK in testing

This Pull Request (PR) fixes the following issues

Task list

  • Added an entry to the change log under the Unreleased section of the file CHANGELOG.md.
    Entry should say what was changed and how that affects users (if applicable), and
    reference the issue being resolved (if applicable).
  • Resource documentation added/updated in README.md.
  • Resource parameter descriptions added/updated in README.md, schema.mof and comment-based
    help.
  • Comment-based help added/updated.
  • Localization strings added/updated in all localization files as appropriate.
  • Examples appropriately added/updated.
  • Unit tests added/updated. See DSC Community Testing Guidelines.
  • Integration tests added/updated (where possible). See DSC Community Testing Guidelines.
  • New/changed code adheres to DSC Community Style Guidelines.

This change is Reviewable

@Borgquite Borgquite marked this pull request as draft October 2, 2025 12:48
Copy link

coderabbitai bot commented Oct 2, 2025

Walkthrough

Adds a public read-only Enabled property to ADReadOnlyDomainControllerAccount; moves OS/domain-controller presence checks into ADDomainController (uses Test-IsDomainController), rehomes domain-controller lookup behavior from ActiveDirectoryDsc.Common into ADDomainController, updates localization/messages and parameter docs, and adapts unit tests to the new control flow.

Changes

Cohort / File(s) Summary of changes
ADDomainController resource
source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
Reworked Get-TargetResource to gate DC-specific work using Test-IsDomainController; when a DC, resolves domain and DC object then gathers RODC-managed-by, password-replication lists, service/registry values and installation flags; when not a DC, returns minimal defaults. Updated verbose/message keys and parameter docs warning against using several params with UseExistingAccount.
ADDomainController schema descriptions
source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.schema.mof
Appended "Should not be used alongside UseExistingAccount parameter." to descriptions for SiteName, IsGlobalCatalog, ReadOnlyReplica, DelegatedAdministratorAccountName, AllowPasswordReplicationAccountName, DenyPasswordReplicationAccountName, and InstallDns.
ADDomainController localization
source/DSCResources/MSFT_ADDomainController/en-US/MSFT_ADDomainController.strings.psd1
Replaced/adjusted string keys: removed old IsDomainController, added IsDomainControllerInDomain, WasExpectingDomainController, and FoundDomainControllerObject messages to reflect new DC-detection and retrieval outcomes.
RODC account resource logic
source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.psm1
Get-TargetResource now returns Enabled in result: domainControllerObject.Enabled when the computer is a read-only DC; otherwise false.
RODC account schema
source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.schema.mof
Added public read-only Boolean property Enabled (Read permission) with descriptive text.
Common module: Get-DomainControllerObject
source/Modules/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.psm1
Removed local-computer post-fetch fallback/check from Get-DomainControllerObject; updated error handling to raise FailedGetDomainController including computer/domain context; generalized doc strings.
Common module docs & localization
source/Modules/ActiveDirectoryDsc.Common/README.md, .../en-US/ActiveDirectoryDsc.Common.strings.psd1
README wording adjusted to "Active Directory domain controller object." Replaced WasExpectingDomainController / FailedEvaluatingDomainController entries with a single FailedGetDomainController message including placeholders for computer and domain.
Unit tests
tests/Unit/MSFT_ADDomainController.Tests.ps1, tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
Replaced/added mocks and assertions to use Test-IsDomainController for DC detection; added scenario where node is a DC but domain/DC object cannot be found; consolidated/updated test contexts and mock invocation counts.
CHANGELOG
CHANGELOG.md
Documents new ADReadOnlyDomainControllerAccount.Enabled, ADDomainController DC-detection fixes/rehoming, ActiveDirectoryDsc.Common changes, localization updates, and parameter documentation notes for UseExistingAccount.

Sequence Diagram(s)

sequenceDiagram
  autonumber
  participant Node
  participant ADDC as ADDomainController
  participant Common as ActiveDirectoryDsc.Common
  participant AD as Active Directory

  Note over ADDC: Get-TargetResource (updated)
  Node->>ADDC: Invoke Get-TargetResource(...)
  ADDC->>ADDC: Test-IsDomainController
  alt Node is DC
    ADDC->>Common: Get-DomainControllerObject(domain, computer)
    Common->>AD: Query DC object
    AD-->>Common: DC object
    Common-->>ADDC: DC object
    ADDC->>AD: Get-DomainObject / PRP / ManagedBy / registry/service checks
    AD-->>ADDC: Domain/DC details
    ADDC-->>Node: return target-state hashtable (includes DC data)
  else Node not DC
    ADDC->>AD: Resolve domain object (non-DC path)
    AD-->>ADDC: Domain object/info
    ADDC-->>Node: return target-state hashtable (minimal/defaults)
  end
Loading
sequenceDiagram
  autonumber
  participant Node
  participant RODC as ADReadOnlyDomainControllerAccount
  participant AD as Active Directory

  Note over RODC: Get-TargetResource (Enabled property)
  Node->>RODC: Invoke Get-TargetResource(...)
  RODC->>AD: Query DC object for node
  AD-->>RODC: DC object (includes IsReadOnly, Enabled)
  alt DC object is read-only
    RODC-->>Node: Return {..., Enabled = DC.Enabled}
  else Not read-only
    RODC-->>Node: Return {..., Enabled = $false}
  end
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

  • Migrate Tests to Pester 5 #741 — Modifies ActiveDirectoryDsc.Common and DC-detection/error messaging; strongly related to the rehoming of DC-detection and related message/key changes.

Pre-merge checks

✅ Passed checks (5 passed)
Check name Status Explanation
Title Check ✅ Passed The title clearly summarizes the primary change by stating that the ADDomainController resource now allows UseExistingAccount to work with pre-staged computer accounts, directly reflecting the main objective of the pull request.
Linked Issues Check ✅ Passed The pull request implements all coding objectives from issue #747 by adding an OS-level Test-IsDomainController check before AD queries, removing duplicate logic from Get-DomainControllerObject, introducing the Enabled property to ADReadOnlyDomainControllerAccount, and updating documentation, schemas, tests, and localization to support UseExistingAccount with pre-staged RODC accounts.
Out of Scope Changes Check ✅ Passed All modifications—including resource logic updates, schema and string adjustments, common function simplifications, and test revisions—directly support the objectives of issue #747, with no unrelated or extraneous changes introduced.
Docstring Coverage ✅ Passed No functions found in the changes. Docstring coverage check skipped.
Description Check ✅ Passed The pull request description clearly outlines the bugs encountered, the specific changes made to address those issues, and the affected resources and functions, demonstrating a direct relationship to the changeset and referencing the resolved issue.

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 5

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.psm1 (1)

12-47: Add OUTPUTS section to comment-based help.

The comment-based help for Get-TargetResource is missing an OUTPUTS section. Per coding guidelines, all functions must document their return types.

Apply this diff to add the OUTPUTS section:

     .PARAMETER InstallDns
         Specifies if the DNS Server service should be installed and configured on
         the read only domain controller. If this is not set the default value of the parameter
         InstallDns of the cmdlet Add-ADDSReadOnlyDomainControllerAccount is used.
         The parameter `InstallDns` is only used during the provisioning of a read only domain
         controller. The parameter cannot be used to install or uninstall the DNS
         server on an already provisioned read only domain controller.
 
         Not used in Get-TargetResource.
 
+    .OUTPUTS
+        System.Collections.Hashtable
+
+        Returns a hashtable containing the current state of the read only domain controller account.
+
     .NOTES
         Used Functions:
             Name                                            | Module
🧹 Nitpick comments (3)
source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.psm1 (3)

127-127: Convert Boolean to String for MOF schema compatibility.

The schema defines Enabled as String (line 14 in schema.mof), but $domainControllerObject.Enabled likely returns a Boolean. While PowerShell auto-converts Boolean to String, explicit conversion ensures schema compliance and clarity.

Apply this diff to explicitly convert to String:

-            Enabled                             = $domainControllerObject.Enabled
+            Enabled                             = $domainControllerObject.Enabled.ToString()

146-146: Convert Boolean to String for MOF schema compatibility.

The schema defines Enabled as String (line 14 in schema.mof), but $false is a Boolean. Apply explicit conversion to ensure schema compliance.

Apply this diff to explicitly convert to String:

-            Enabled                             = $false
+            Enabled                             = $false.ToString()

12-47: Add .OUTPUTS section to comment-based help.

The comment-based help is missing an .OUTPUTS section documenting the returned hashtable and its properties (including the newly added Enabled property).

Add the following section to the comment-based help:

     .NOTES
         Used Functions:
             Name                                            | Module
             ------------------------------------------------|--------------------------
             Get-ADDomain                                    | ActiveDirectory
             Get-ADDomainControllerPasswordReplicationPolicy | ActiveDirectory
             Get-DomainControllerObject                      | ActiveDirectoryDsc.Common
             Assert-Module                                   | DscResource.Common
             New-ObjectNotFoundException                     | DscResource.Common
+
+    .OUTPUTS
+        System.Collections.Hashtable
+
+        Returns a hashtable containing the current state of the Read Only Domain Controller Account with properties: AllowPasswordReplicationAccountName, Credential, DelegatedAdministratorAccountName, DenyPasswordReplicationAccountName, DomainControllerAccountName, DomainName, Enabled, Ensure, InstallDns, IsGlobalCatalog, and SiteName.
 #>
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 4751ae1 and b3ff22a.

📒 Files selected for processing (9)
  • CHANGELOG.md (1 hunks)
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (5 hunks)
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.schema.mof (1 hunks)
  • source/DSCResources/MSFT_ADDomainController/en-US/MSFT_ADDomainController.strings.psd1 (1 hunks)
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.psm1 (2 hunks)
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.schema.mof (1 hunks)
  • source/Modules/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.psm1 (2 hunks)
  • source/Modules/ActiveDirectoryDsc.Common/README.md (1 hunks)
  • source/Modules/ActiveDirectoryDsc.Common/en-US/ActiveDirectoryDsc.Common.strings.psd1 (1 hunks)
🧰 Additional context used
📓 Path-based instructions (5)
**

⚙️ CodeRabbit configuration file

**: # DSC Community Guidelines

Terminology

  • Command: Public command
  • Function: Private function
  • Resource: DSC class-based resource

Build & Test Workflow Requirements

  • Run PowerShell script files from repository root
  • Setup build and test environment (once per pwsh session): ./build.ps1 -Tasks noop
  • Build project before running tests: ./build.ps1 -Tasks build
  • Always run tests in new pwsh session: Invoke-Pester -Path @({test paths}) -Output Detailed

File Organization

  • Public commands: source/Public/{CommandName}.ps1
  • Private functions: source/Private/{FunctionName}.ps1
  • Unit tests: tests/Unit/{Classes|Public|Private}/{Name}.Tests.ps1
  • Integration tests: tests/Integration/Commands/{CommandName}.Integration.Tests.ps1

Requirements

  • Follow instructions over existing code patterns
  • Follow PowerShell style and test guideline instructions strictly
  • Always update CHANGELOG.md Unreleased section
  • Localize all strings using string keys; remove any orphaned string keys
  • Check DscResource.Common before creating private functions
  • Separate reusable logic into private functions
  • DSC resources should always be created as class-based resources
  • Add unit tests for all commands/functions/resources
  • Add integration tests for all public commands and resources

Files:

  • source/Modules/ActiveDirectoryDsc.Common/README.md
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.schema.mof
  • source/Modules/ActiveDirectoryDsc.Common/en-US/ActiveDirectoryDsc.Common.strings.psd1
  • source/Modules/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.psm1
  • source/DSCResources/MSFT_ADDomainController/en-US/MSFT_ADDomainController.strings.psd1
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.schema.mof
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • CHANGELOG.md
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.psm1
**/*.md

⚙️ CodeRabbit configuration file

**/*.md: # Markdown Style Guidelines

  • Wrap lines at word boundaries when over 80 characters (except tables/code blocks)
  • Use 2 spaces for indentation
  • Use '1.' for all items in ordered lists (1/1/1 numbering style)
  • Disable MD013 rule by adding a comment for tables/code blocks exceeding 80 characters
  • Empty lines required before/after code blocks and headings (except before line 1)
  • Escape backslashes in file paths only (not in code blocks)
  • Code blocks must specify language identifiers

Text Formatting

  • Parameters: bold
  • Values/literals: inline code
  • Resource/module/product names: italic
  • Commands/files/paths: inline code

Files:

  • source/Modules/ActiveDirectoryDsc.Common/README.md
  • CHANGELOG.md
{**/*.ps1,**/*.psm1,**/*.psd1}

⚙️ CodeRabbit configuration file

{**/*.ps1,**/*.psm1,**/*.psd1}: # PowerShell Guidelines

Naming

  • Use descriptive names (3+ characters, no abbreviations)
  • Functions: PascalCase with Verb-Noun format using approved verbs
  • Parameters: PascalCase
  • Variables: camelCase
  • Keywords: lower-case
  • Classes: PascalCase
  • Include scope for script/global/environment variables: $script:, $global:, $env:

File naming

  • Class files: ###.ClassName.ps1 format (e.g. 001.SqlReason.ps1, 004.StartupParameters.ps1)

Formatting

Indentation & Spacing

  • Use 4 spaces (no tabs)
  • One space around operators: $a = 1 + 2
  • One space between type and variable: [String] $name
  • One space between keyword and parenthesis: if ($condition)
  • No spaces on empty lines
  • Try to limit lines to 120 characters

Braces

  • Newline before opening brace (except variable assignments)
  • One newline after opening brace
  • Two newlines after closing brace (one if followed by another brace or continuation)

Quotes

  • Use single quotes unless variable expansion is needed: 'text' vs "text $variable"

Arrays

  • Single line: @('one', 'two', 'three')
  • Multi-line: each element on separate line with proper indentation
  • Do not use the unary comma operator (,) in return statements to force
    an array

Hashtables

  • Empty: @{}
  • Each property on separate line with proper indentation
  • Properties: Use PascalCase

Comments

  • Single line: # Comment (capitalized, on own line)
  • Multi-line: <# Comment #> format (opening and closing brackets on own line), and indent text
  • No commented-out code

Comment-based help

  • Always add comment-based help to all functions and scripts
  • Comment-based help: SYNOPSIS, DESCRIPTION (40+ chars), PARAMETER, EXAMPLE sections before function/class
  • Comment-based help indentation: keywords 4 spaces, text 8 spaces
  • Include examples for all parameter sets and combinations
  • INPUTS: List each pipeline‑accepted type (one per line) with a 1‑line description...

Files:

  • source/Modules/ActiveDirectoryDsc.Common/en-US/ActiveDirectoryDsc.Common.strings.psd1
  • source/Modules/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.psm1
  • source/DSCResources/MSFT_ADDomainController/en-US/MSFT_ADDomainController.strings.psd1
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.psm1
source/DSCResources/**/*.psm1

⚙️ CodeRabbit configuration file

source/DSCResources/**/*.psm1: # MOF-based Desired State Configuration (DSC) Resources Guidelines

Required Functions

  • Every DSC resource must define: Get-TargetResource, Set-TargetResource, Test-TargetResource
  • Export using *-TargetResource pattern

Function Return Types

  • Get-TargetResource: Must return hashtable with all resource properties
  • Test-TargetResource: Must return boolean ($true/$false)
  • Set-TargetResource: Must not return anything (void)

Parameter Guidelines

  • Get-TargetResource: Only include parameters needed to retrieve actual current state values
  • Get-TargetResource: Remove non-mandatory parameters that are never used
  • Set-TargetResource and Test-TargetResource: Must have identical parameters
  • Set-TargetResource and Test-TargetResource: Unused mandatory parameters: Add "Not used in <function_name>" to help comment

Required Elements

  • Each function must include Write-Verbose at least once
    • Get-TargetResource: Use verbose message starting with "Getting the current state of..."
    • Set-TargetResource: Use verbose message starting with "Setting the desired state of..."
    • Test-TargetResource: Use verbose message starting with "Determining the current state of..."
  • Use localized strings for all messages (Write-Verbose, Write-Error, etc.)
  • Import localized strings using Get-LocalizedData at module top

Error Handling

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.psm1
CHANGELOG.md

⚙️ CodeRabbit configuration file

CHANGELOG.md: # Changelog Guidelines

  • Always update the Unreleased section in CHANGELOG.md
  • Use Keep a Changelog format
  • Describe notable changes briefly, ≤2 items per change type
  • Reference issues using format issue #<issue_number>
  • No empty lines between list items in same section
  • Skip adding entry if same change already exists in Unreleased section
  • No duplicate sections or items in Unreleased section

Files:

  • CHANGELOG.md
🪛 markdownlint-cli2 (0.18.1)
CHANGELOG.md

17-17: Headings should be surrounded by blank lines
Expected: 1; Actual: 0; Below

(MD022, blanks-around-headings)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Test Unit)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Test HQRM)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Build Package Module)
🔇 Additional comments (12)
source/Modules/ActiveDirectoryDsc.Common/README.md (1)

65-65: Doc tweak looks good

Updated summary matches the streamlined function behavior.

source/Modules/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.psm1 (2)

1286-1289: LGTM!

The documentation wording is now more precise and aligned with Microsoft Active Directory terminology.


1353-1354: LGTM!

The error message is now more descriptive, including both computer name and domain for better diagnostics. The validation logic has been appropriately moved to the calling code in ADDomainController resource.

source/Modules/ActiveDirectoryDsc.Common/en-US/ActiveDirectoryDsc.Common.strings.psd1 (1)

4-4: LGTM!

The new localization key provides clearer error messaging with both computer and domain context. The message is properly formatted with parameter placeholders.

source/DSCResources/MSFT_ADDomainController/en-US/MSFT_ADDomainController.strings.psd1 (1)

4-7: LGTM!

The localization updates support the new control flow effectively:

  • IsDomainController provides initial OS-level detection feedback
  • WasExpectingDomainController handles the edge case where OS indicates DC but object retrieval fails
  • FoundDomainControllerObject confirms successful retrieval with domain context

The messages are clear and provide appropriate diagnostic information at each stage of the verification process.

source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.schema.mof (1)

10-19: Usage constraints documented but not enforced.

The schema correctly documents that these parameters should not be used with UseExistingAccount. However, as noted in the PR description, no hard enforcement is implemented. Consider whether parameter validation rules should be added to prevent invalid parameter combinations at runtime.

Do you want me to generate validation logic that enforces these constraints in the *-TargetResource functions?

source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (4)

106-114: LGTM!

The password replication policy and service configuration retrieval logic is correct:

  • Uses appropriate AD cmdlets for RODC policies
  • Registry paths are correct for NTDS and NETLOGON services
  • DNS service check properly handles service not found with ErrorAction SilentlyContinue

136-139: Appropriate error handling for edge case.

The error path correctly handles the scenario where:

  • The OS indicates the node is a domain controller (Test-IsDomainController returns $true)
  • But Get-DomainControllerObject returns $null or fails

This could occur during initial promotion or in error conditions. The error message clearly describes the situation.


195-233: LGTM!

The parameter descriptions correctly document the constraint that these parameters should not be used with UseExistingAccount. This is consistent with the schema.mof documentation and helps users understand the limitation when working with pre-staged RODC accounts.


681-719: LGTM!

The parameter descriptions are consistently documented across all three functions (Get/Set/Test-TargetResource) and match the schema.mof documentation. This provides clear guidance to users about parameter usage constraints with pre-staged accounts.

source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.psm1 (2)

127-127: LGTM!

The addition of the Enabled property correctly surfaces the read-only domain controller account's enabled state from the AD object.


146-146: LGTM!

The fallback value of $false for Enabled is appropriate when the account is not a read-only domain controller.

Borgquite and others added 2 commits October 2, 2025 13:57
Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>
…T_ADReadOnlyDomainControllerAccount.schema.mof

Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (1)
CHANGELOG.md (1)

12-13: Consider refining wording for clarity.

The phrase "stating whether" could be replaced with "indicating whether" for more idiomatic English.

Apply this diff:

 - ADReadOnlyDomainControllerAccount
-  - Added read-only value Enabled stating whether a pre-staged account is Enabled or Disabled (Unoccupied).
+  - Added read-only value Enabled indicating whether a pre-staged account is Enabled or Disabled (Unoccupied).
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between b3ff22a and 1436d47.

📒 Files selected for processing (2)
  • CHANGELOG.md (1 hunks)
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.schema.mof (1 hunks)
🧰 Additional context used
📓 Path-based instructions (3)
**

⚙️ CodeRabbit configuration file

**: # DSC Community Guidelines

Terminology

  • Command: Public command
  • Function: Private function
  • Resource: DSC class-based resource

Build & Test Workflow Requirements

  • Run PowerShell script files from repository root
  • Setup build and test environment (once per pwsh session): ./build.ps1 -Tasks noop
  • Build project before running tests: ./build.ps1 -Tasks build
  • Always run tests in new pwsh session: Invoke-Pester -Path @({test paths}) -Output Detailed

File Organization

  • Public commands: source/Public/{CommandName}.ps1
  • Private functions: source/Private/{FunctionName}.ps1
  • Unit tests: tests/Unit/{Classes|Public|Private}/{Name}.Tests.ps1
  • Integration tests: tests/Integration/Commands/{CommandName}.Integration.Tests.ps1

Requirements

  • Follow instructions over existing code patterns
  • Follow PowerShell style and test guideline instructions strictly
  • Always update CHANGELOG.md Unreleased section
  • Localize all strings using string keys; remove any orphaned string keys
  • Check DscResource.Common before creating private functions
  • Separate reusable logic into private functions
  • DSC resources should always be created as class-based resources
  • Add unit tests for all commands/functions/resources
  • Add integration tests for all public commands and resources

Files:

  • CHANGELOG.md
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.schema.mof
**/*.md

⚙️ CodeRabbit configuration file

**/*.md: # Markdown Style Guidelines

  • Wrap lines at word boundaries when over 80 characters (except tables/code blocks)
  • Use 2 spaces for indentation
  • Use '1.' for all items in ordered lists (1/1/1 numbering style)
  • Disable MD013 rule by adding a comment for tables/code blocks exceeding 80 characters
  • Empty lines required before/after code blocks and headings (except before line 1)
  • Escape backslashes in file paths only (not in code blocks)
  • Code blocks must specify language identifiers

Text Formatting

  • Parameters: bold
  • Values/literals: inline code
  • Resource/module/product names: italic
  • Commands/files/paths: inline code

Files:

  • CHANGELOG.md
CHANGELOG.md

⚙️ CodeRabbit configuration file

CHANGELOG.md: # Changelog Guidelines

  • Always update the Unreleased section in CHANGELOG.md
  • Use Keep a Changelog format
  • Describe notable changes briefly, ≤2 items per change type
  • Reference issues using format issue #<issue_number>
  • No empty lines between list items in same section
  • Skip adding entry if same change already exists in Unreleased section
  • No duplicate sections or items in Unreleased section

Files:

  • CHANGELOG.md
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Test Unit)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Test HQRM)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Build Package Module)
🔇 Additional comments (2)
source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.schema.mof (1)

14-14: LGTM! Type mismatch resolved.

The Enabled property is now correctly declared as Boolean, matching the implementation that returns Boolean values from Get-TargetResource.

CHANGELOG.md (1)

19-24: LGTM! Fixed section properly formatted.

The Fixed section entries correctly describe the changes with appropriate detail and issue references. The blank line after the heading is present, resolving the previous markdown lint issue.

@Borgquite Borgquite changed the title ADDomainController: Allow UseExistingParameter to work when using pre-staged computer account ADDomainController: Allow UseExistingAccount to work when using pre-staged computer account Oct 2, 2025
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between b3ff22a and 57d4b9c.

📒 Files selected for processing (3)
  • CHANGELOG.md (1 hunks)
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.schema.mof (1 hunks)
  • tests/Unit/MSFT_ADDomainController.Tests.ps1 (7 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • source/DSCResources/MSFT_ADReadOnlyDomainControllerAccount/MSFT_ADReadOnlyDomainControllerAccount.schema.mof
🧰 Additional context used
📓 Path-based instructions (6)
**

⚙️ CodeRabbit configuration file

**: # DSC Community Guidelines

Terminology

  • Command: Public command
  • Function: Private function
  • Resource: DSC class-based resource

Build & Test Workflow Requirements

  • Run PowerShell script files from repository root
  • Setup build and test environment (once per pwsh session): ./build.ps1 -Tasks noop
  • Build project before running tests: ./build.ps1 -Tasks build
  • Always run tests in new pwsh session: Invoke-Pester -Path @({test paths}) -Output Detailed

File Organization

  • Public commands: source/Public/{CommandName}.ps1
  • Private functions: source/Private/{FunctionName}.ps1
  • Unit tests: tests/Unit/{Classes|Public|Private}/{Name}.Tests.ps1
  • Integration tests: tests/Integration/Commands/{CommandName}.Integration.Tests.ps1

Requirements

  • Follow instructions over existing code patterns
  • Follow PowerShell style and test guideline instructions strictly
  • Always update CHANGELOG.md Unreleased section
  • Localize all strings using string keys; remove any orphaned string keys
  • Check DscResource.Common before creating private functions
  • Separate reusable logic into private functions
  • DSC resources should always be created as class-based resources
  • Add unit tests for all commands/functions/resources
  • Add integration tests for all public commands and resources

Files:

  • CHANGELOG.md
  • tests/Unit/MSFT_ADDomainController.Tests.ps1
**/*.md

⚙️ CodeRabbit configuration file

**/*.md: # Markdown Style Guidelines

  • Wrap lines at word boundaries when over 80 characters (except tables/code blocks)
  • Use 2 spaces for indentation
  • Use '1.' for all items in ordered lists (1/1/1 numbering style)
  • Disable MD013 rule by adding a comment for tables/code blocks exceeding 80 characters
  • Empty lines required before/after code blocks and headings (except before line 1)
  • Escape backslashes in file paths only (not in code blocks)
  • Code blocks must specify language identifiers

Text Formatting

  • Parameters: bold
  • Values/literals: inline code
  • Resource/module/product names: italic
  • Commands/files/paths: inline code

Files:

  • CHANGELOG.md
CHANGELOG.md

⚙️ CodeRabbit configuration file

CHANGELOG.md: # Changelog Guidelines

  • Always update the Unreleased section in CHANGELOG.md
  • Use Keep a Changelog format
  • Describe notable changes briefly, ≤2 items per change type
  • Reference issues using format issue #<issue_number>
  • No empty lines between list items in same section
  • Skip adding entry if same change already exists in Unreleased section
  • No duplicate sections or items in Unreleased section

Files:

  • CHANGELOG.md
tests/[Uu]nit/**/*.[Tt]ests.ps1

⚙️ CodeRabbit configuration file

tests/[Uu]nit/**/*.[Tt]ests.ps1: # Unit Tests Guidelines

  • Test with localized strings: Use InModuleScope -ScriptBlock { $script:localizedData.Key }
  • Mock files: Use $TestDrive variable (path to the test drive)
  • All public commands require parameter set validation tests
  • After modifying classes, always run tests in new session (for changes to take effect)

Test Setup Requirements

Use this exact setup block before Describe:

[System.Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSUseDeclaredVarsMoreThanAssignments', '', Justification = 'Suppressing this rule because Script Analyzer does not understand Pester syntax.')]
param ()

BeforeDiscovery {
    try
    {
        if (-not (Get-Module -Name 'DscResource.Test'))
        {
            # Assumes dependencies have been resolved, so if this module is not available, run 'noop' task.
            if (-not (Get-Module -Name 'DscResource.Test' -ListAvailable))
            {
                # Redirect all streams to $null, except the error stream (stream 2)
                & "$PSScriptRoot/../../../build.ps1" -Tasks 'noop' 3>&1 4>&1 5>&1 6>&1 > $null
            }

            # If the dependencies have not been resolved, this will throw an error.
            Import-Module -Name 'DscResource.Test' -Force -ErrorAction 'Stop'
        }
    }
    catch [System.IO.FileNotFoundException]
    {
        throw 'DscResource.Test module dependency not found. Please run ".\build.ps1 -ResolveDependency -Tasks noop" first.'
    }
}

BeforeAll {
    $script:moduleName = '{MyModuleName}'

    Import-Module -Name $script:moduleName -Force -ErrorAction 'Stop'

    $PSDefaultParameterValues['InModuleScope:ModuleName'] = $script:moduleName
    $PSDefaultParameterValues['Mock:ModuleName'] = $script:moduleName
    $PSDefaultParameterValues['Should:ModuleName'] = $script:moduleName
}

AfterAll {
    $PSDefaultParameterValues.Remove('InModuleScope:ModuleName')
    $PSDefaultParameterValues.Remove('Mock:ModuleNam...

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
{**/*.ps1,**/*.psm1,**/*.psd1}

⚙️ CodeRabbit configuration file

{**/*.ps1,**/*.psm1,**/*.psd1}: # PowerShell Guidelines

Naming

  • Use descriptive names (3+ characters, no abbreviations)
  • Functions: PascalCase with Verb-Noun format using approved verbs
  • Parameters: PascalCase
  • Variables: camelCase
  • Keywords: lower-case
  • Classes: PascalCase
  • Include scope for script/global/environment variables: $script:, $global:, $env:

File naming

  • Class files: ###.ClassName.ps1 format (e.g. 001.SqlReason.ps1, 004.StartupParameters.ps1)

Formatting

Indentation & Spacing

  • Use 4 spaces (no tabs)
  • One space around operators: $a = 1 + 2
  • One space between type and variable: [String] $name
  • One space between keyword and parenthesis: if ($condition)
  • No spaces on empty lines
  • Try to limit lines to 120 characters

Braces

  • Newline before opening brace (except variable assignments)
  • One newline after opening brace
  • Two newlines after closing brace (one if followed by another brace or continuation)

Quotes

  • Use single quotes unless variable expansion is needed: 'text' vs "text $variable"

Arrays

  • Single line: @('one', 'two', 'three')
  • Multi-line: each element on separate line with proper indentation
  • Do not use the unary comma operator (,) in return statements to force
    an array

Hashtables

  • Empty: @{}
  • Each property on separate line with proper indentation
  • Properties: Use PascalCase

Comments

  • Single line: # Comment (capitalized, on own line)
  • Multi-line: <# Comment #> format (opening and closing brackets on own line), and indent text
  • No commented-out code

Comment-based help

  • Always add comment-based help to all functions and scripts
  • Comment-based help: SYNOPSIS, DESCRIPTION (40+ chars), PARAMETER, EXAMPLE sections before function/class
  • Comment-based help indentation: keywords 4 spaces, text 8 spaces
  • Include examples for all parameter sets and combinations
  • INPUTS: List each pipeline‑accepted type (one per line) with a 1‑line description...

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
**/*.[Tt]ests.ps1

⚙️ CodeRabbit configuration file

**/*.[Tt]ests.ps1: # Tests Guidelines

Core Requirements

  • All public commands, private functions and classes must have unit tests
  • All public commands and class-based resources must have integration tests
  • Use Pester v5 syntax only
  • Test code only inside Describe blocks
  • Assertions only in It blocks
  • Never test verbose messages, debug messages or parameter binding behavior
  • Pass all mandatory parameters to avoid prompts

Requirements

  • Inside It blocks, assign unused return objects to $null (unless part of pipeline)
  • Tested entity must be called from within the It blocks
  • Keep results and assertions in same It block
  • Avoid try-catch-finally for cleanup, use AfterAll or AfterEach
  • Avoid unnecessary remove/recreate cycles

Naming

  • One Describe block per file matching the tested entity name
  • Context descriptions start with 'When'
  • It descriptions start with 'Should', must not contain 'when'
  • Mock variables prefix: 'mock'

Structure & Scope

  • Public commands: Never use InModuleScope (unless retrieving localized strings)
  • Private functions/class resources: Always use InModuleScope
  • Each class method = separate Context block
  • Each scenario = separate Context block
  • Use nested Context blocks for complex scenarios
  • Mocking in BeforeAll (BeforeEach only when required)
  • Setup/teardown in BeforeAll,BeforeEach/AfterAll,AfterEach close to usage

Syntax Rules

  • PascalCase: Describe, Context, It, Should, BeforeAll, BeforeEach, AfterAll, AfterEach
  • Use -BeTrue/-BeFalse never -Be $true/-Be $false
  • Never use Assert-MockCalled, use Should -Invoke instead
  • No Should -Not -Throw - invoke commands directly
  • Never add an empty -MockWith block
  • Omit -MockWith when returning $null
  • Set $PSDefaultParameterValues for Mock:ModuleName, Should:ModuleName, InModuleScope:ModuleName
  • Omit -ModuleName parameter on Pester commands
  • Never use Mock inside `InModuleSc...

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
🧠 Learnings (2)
📚 Learning: 2025-09-12T13:21:31.054Z
Learnt from: CR
PR: dsccommunity/SqlServerDsc#0
File: .github/instructions/dsc-community-style-guidelines-pester.instructions.md:0-0
Timestamp: 2025-09-12T13:21:31.054Z
Learning: Applies to **/*.[Tt]ests.ps1 : Perform mocking in BeforeAll (use BeforeEach only when required)

Applied to files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
📚 Learning: 2025-09-12T13:21:31.054Z
Learnt from: CR
PR: dsccommunity/SqlServerDsc#0
File: .github/instructions/dsc-community-style-guidelines-pester.instructions.md:0-0
Timestamp: 2025-09-12T13:21:31.054Z
Learning: Applies to **/*.[Tt]ests.ps1 : Set $PSDefaultParameterValues for Mock:ModuleName, Should:ModuleName, and InModuleScope:ModuleName

Applied to files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
🔇 Additional comments (2)
tests/Unit/MSFT_ADDomainController.Tests.ps1 (2)

66-66: LGTM!

The Test-IsDomainController mocks and assertions correctly verify domain controller state checks in scenarios where the node is a domain controller.

Also applies to: 88-88, 96-96, 151-151, 196-196, 279-279


293-293: LGTM!

The context name change improves clarity by describing the actual state ("is not") rather than the desired state ("should not be").

Copy link
Contributor Author

@Borgquite Borgquite left a comment

Choose a reason for hiding this comment

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

Reviewable status: 0 of 10 files reviewed, 3 unresolved discussions

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (3)
tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1 (1)

24-25: Align dependency error hint with guidelines ('noop' task).

Use '-Tasks noop' in the guidance message for consistency.

As per coding guidelines

-        throw 'DscResource.Test module dependency not found. Please run ".\build.ps1 -ResolveDependency -Tasks build" first.'
+        throw 'DscResource.Test module dependency not found. Please run ".\build.ps1 -ResolveDependency -Tasks noop" first.'
tests/Unit/MSFT_ADDomainController.Tests.ps1 (1)

24-25: Align dependency error hint with guidelines ('noop' task).

Use '-Tasks noop' in the guidance message for consistency.

As per coding guidelines

-        throw 'DscResource.Test module dependency not found. Please run ".\build.ps1 -ResolveDependency -Tasks build" first.'
+        throw 'DscResource.Test module dependency not found. Please run ".\build.ps1 -ResolveDependency -Tasks noop" first.'
source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (1)

96-107: Add defensive null checks for nested AD lookups.

Guard ComputerObjectDN and the returned computer object before accessing ManagedBy; keeps behavior robust in edge AD states.

Apply:

-                $domainControllerComputerObject = $domainControllerObject.ComputerObjectDN |
-                    Get-ADComputer -Properties ManagedBy -Credential $Credential
-                if ($domainControllerComputerObject.ManagedBy)
+                if ($domainControllerObject.ComputerObjectDN)
                 {
-                    $domainControllerManagedByObject = $domainControllerComputerObject.ManagedBy |
-                        Get-ADObject -Properties objectSid -Credential $Credential
+                    $domainControllerComputerObject = $domainControllerObject.ComputerObjectDN |
+                        Get-ADComputer -Properties ManagedBy -Credential $Credential
+
+                    if ($domainControllerComputerObject -and $domainControllerComputerObject.ManagedBy)
+                    {
+                        $domainControllerManagedByObject = $domainControllerComputerObject.ManagedBy |
+                            Get-ADObject -Properties objectSid -Credential $Credential
+                    }
 
-                    if ($domainControllerManagedByObject.objectSid)
+                    if ($domainControllerManagedByObject -and $domainControllerManagedByObject.objectSid)
                     {
                         $delegateAdministratorAccountName = Resolve-SamAccountName -ObjectSid $domainControllerManagedByObject.objectSid
                     }
                 }

Based on learnings

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 331fc98 and bc01650.

📒 Files selected for processing (3)
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (6 hunks)
  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1 (2 hunks)
  • tests/Unit/MSFT_ADDomainController.Tests.ps1 (7 hunks)
🧰 Additional context used
📓 Path-based instructions (5)
**

⚙️ CodeRabbit configuration file

**: # DSC Community Guidelines

Terminology

  • Command: Public command
  • Function: Private function
  • Resource: DSC class-based resource

Build & Test Workflow Requirements

  • Run PowerShell script files from repository root
  • Setup build and test environment (once per pwsh session): ./build.ps1 -Tasks noop
  • Build project before running tests: ./build.ps1 -Tasks build
  • Always run tests in new pwsh session: Invoke-Pester -Path @({test paths}) -Output Detailed

File Organization

  • Public commands: source/Public/{CommandName}.ps1
  • Private functions: source/Private/{FunctionName}.ps1
  • Unit tests: tests/Unit/{Classes|Public|Private}/{Name}.Tests.ps1
  • Integration tests: tests/Integration/Commands/{CommandName}.Integration.Tests.ps1

Requirements

  • Follow instructions over existing code patterns
  • Follow PowerShell style and test guideline instructions strictly
  • Always update CHANGELOG.md Unreleased section
  • Localize all strings using string keys; remove any orphaned string keys
  • Check DscResource.Common before creating private functions
  • Separate reusable logic into private functions
  • DSC resources should always be created as class-based resources
  • Add unit tests for all commands/functions/resources
  • Add integration tests for all public commands and resources

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
tests/[Uu]nit/**/*.[Tt]ests.ps1

⚙️ CodeRabbit configuration file

tests/[Uu]nit/**/*.[Tt]ests.ps1: # Unit Tests Guidelines

  • Test with localized strings: Use InModuleScope -ScriptBlock { $script:localizedData.Key }
  • Mock files: Use $TestDrive variable (path to the test drive)
  • All public commands require parameter set validation tests
  • After modifying classes, always run tests in new session (for changes to take effect)

Test Setup Requirements

Use this exact setup block before Describe:

[System.Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSUseDeclaredVarsMoreThanAssignments', '', Justification = 'Suppressing this rule because Script Analyzer does not understand Pester syntax.')]
param ()

BeforeDiscovery {
    try
    {
        if (-not (Get-Module -Name 'DscResource.Test'))
        {
            # Assumes dependencies have been resolved, so if this module is not available, run 'noop' task.
            if (-not (Get-Module -Name 'DscResource.Test' -ListAvailable))
            {
                # Redirect all streams to $null, except the error stream (stream 2)
                & "$PSScriptRoot/../../../build.ps1" -Tasks 'noop' 3>&1 4>&1 5>&1 6>&1 > $null
            }

            # If the dependencies have not been resolved, this will throw an error.
            Import-Module -Name 'DscResource.Test' -Force -ErrorAction 'Stop'
        }
    }
    catch [System.IO.FileNotFoundException]
    {
        throw 'DscResource.Test module dependency not found. Please run ".\build.ps1 -ResolveDependency -Tasks noop" first.'
    }
}

BeforeAll {
    $script:moduleName = '{MyModuleName}'

    Import-Module -Name $script:moduleName -Force -ErrorAction 'Stop'

    $PSDefaultParameterValues['InModuleScope:ModuleName'] = $script:moduleName
    $PSDefaultParameterValues['Mock:ModuleName'] = $script:moduleName
    $PSDefaultParameterValues['Should:ModuleName'] = $script:moduleName
}

AfterAll {
    $PSDefaultParameterValues.Remove('InModuleScope:ModuleName')
    $PSDefaultParameterValues.Remove('Mock:ModuleNam...

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
{**/*.ps1,**/*.psm1,**/*.psd1}

⚙️ CodeRabbit configuration file

{**/*.ps1,**/*.psm1,**/*.psd1}: # PowerShell Guidelines

Naming

  • Use descriptive names (3+ characters, no abbreviations)
  • Functions: PascalCase with Verb-Noun format using approved verbs
  • Parameters: PascalCase
  • Variables: camelCase
  • Keywords: lower-case
  • Classes: PascalCase
  • Include scope for script/global/environment variables: $script:, $global:, $env:

File naming

  • Class files: ###.ClassName.ps1 format (e.g. 001.SqlReason.ps1, 004.StartupParameters.ps1)

Formatting

Indentation & Spacing

  • Use 4 spaces (no tabs)
  • One space around operators: $a = 1 + 2
  • One space between type and variable: [String] $name
  • One space between keyword and parenthesis: if ($condition)
  • No spaces on empty lines
  • Try to limit lines to 120 characters

Braces

  • Newline before opening brace (except variable assignments)
  • One newline after opening brace
  • Two newlines after closing brace (one if followed by another brace or continuation)

Quotes

  • Use single quotes unless variable expansion is needed: 'text' vs "text $variable"

Arrays

  • Single line: @('one', 'two', 'three')
  • Multi-line: each element on separate line with proper indentation
  • Do not use the unary comma operator (,) in return statements to force
    an array

Hashtables

  • Empty: @{}
  • Each property on separate line with proper indentation
  • Properties: Use PascalCase

Comments

  • Single line: # Comment (capitalized, on own line)
  • Multi-line: <# Comment #> format (opening and closing brackets on own line), and indent text
  • No commented-out code

Comment-based help

  • Always add comment-based help to all functions and scripts
  • Comment-based help: SYNOPSIS, DESCRIPTION (40+ chars), PARAMETER, EXAMPLE sections before function/class
  • Comment-based help indentation: keywords 4 spaces, text 8 spaces
  • Include examples for all parameter sets and combinations
  • INPUTS: List each pipeline‑accepted type (one per line) with a 1‑line description...

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
**/*.[Tt]ests.ps1

⚙️ CodeRabbit configuration file

**/*.[Tt]ests.ps1: # Tests Guidelines

Core Requirements

  • All public commands, private functions and classes must have unit tests
  • All public commands and class-based resources must have integration tests
  • Use Pester v5 syntax only
  • Test code only inside Describe blocks
  • Assertions only in It blocks
  • Never test verbose messages, debug messages or parameter binding behavior
  • Pass all mandatory parameters to avoid prompts

Requirements

  • Inside It blocks, assign unused return objects to $null (unless part of pipeline)
  • Tested entity must be called from within the It blocks
  • Keep results and assertions in same It block
  • Avoid try-catch-finally for cleanup, use AfterAll or AfterEach
  • Avoid unnecessary remove/recreate cycles

Naming

  • One Describe block per file matching the tested entity name
  • Context descriptions start with 'When'
  • It descriptions start with 'Should', must not contain 'when'
  • Mock variables prefix: 'mock'

Structure & Scope

  • Public commands: Never use InModuleScope (unless retrieving localized strings)
  • Private functions/class resources: Always use InModuleScope
  • Each class method = separate Context block
  • Each scenario = separate Context block
  • Use nested Context blocks for complex scenarios
  • Mocking in BeforeAll (BeforeEach only when required)
  • Setup/teardown in BeforeAll,BeforeEach/AfterAll,AfterEach close to usage

Syntax Rules

  • PascalCase: Describe, Context, It, Should, BeforeAll, BeforeEach, AfterAll, AfterEach
  • Use -BeTrue/-BeFalse never -Be $true/-Be $false
  • Never use Assert-MockCalled, use Should -Invoke instead
  • No Should -Not -Throw - invoke commands directly
  • Never add an empty -MockWith block
  • Omit -MockWith when returning $null
  • Set $PSDefaultParameterValues for Mock:ModuleName, Should:ModuleName, InModuleScope:ModuleName
  • Omit -ModuleName parameter on Pester commands
  • Never use Mock inside `InModuleSc...

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
source/DSCResources/**/*.psm1

⚙️ CodeRabbit configuration file

source/DSCResources/**/*.psm1: # MOF-based Desired State Configuration (DSC) Resources Guidelines

Required Functions

  • Every DSC resource must define: Get-TargetResource, Set-TargetResource, Test-TargetResource
  • Export using *-TargetResource pattern

Function Return Types

  • Get-TargetResource: Must return hashtable with all resource properties
  • Test-TargetResource: Must return boolean ($true/$false)
  • Set-TargetResource: Must not return anything (void)

Parameter Guidelines

  • Get-TargetResource: Only include parameters needed to retrieve actual current state values
  • Get-TargetResource: Remove non-mandatory parameters that are never used
  • Set-TargetResource and Test-TargetResource: Must have identical parameters
  • Set-TargetResource and Test-TargetResource: Unused mandatory parameters: Add "Not used in <function_name>" to help comment

Required Elements

  • Each function must include Write-Verbose at least once
    • Get-TargetResource: Use verbose message starting with "Getting the current state of..."
    • Set-TargetResource: Use verbose message starting with "Setting the desired state of..."
    • Test-TargetResource: Use verbose message starting with "Determining the current state of..."
  • Use localized strings for all messages (Write-Verbose, Write-Error, etc.)
  • Import localized strings using Get-LocalizedData at module top

Error Handling

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
🧠 Learnings (3)
📚 Learning: 2025-09-12T13:21:31.054Z
Learnt from: CR
PR: dsccommunity/SqlServerDsc#0
File: .github/instructions/dsc-community-style-guidelines-pester.instructions.md:0-0
Timestamp: 2025-09-12T13:21:31.054Z
Learning: Applies to **/*.[Tt]ests.ps1 : Perform mocking in BeforeAll (use BeforeEach only when required)

Applied to files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
📚 Learning: 2025-09-12T13:21:31.054Z
Learnt from: CR
PR: dsccommunity/SqlServerDsc#0
File: .github/instructions/dsc-community-style-guidelines-pester.instructions.md:0-0
Timestamp: 2025-09-12T13:21:31.054Z
Learning: Applies to **/*.[Tt]ests.ps1 : Set $PSDefaultParameterValues for Mock:ModuleName, Should:ModuleName, and InModuleScope:ModuleName

Applied to files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
📚 Learning: 2025-08-16T13:35:08.323Z
Learnt from: johlju
PR: dsccommunity/SqlServerDsc#2134
File: source/Public/Get-SqlDscLogin.ps1:0-0
Timestamp: 2025-08-16T13:35:08.323Z
Learning: In PowerShell, users expect to receive $null when no objects are found or when a non-terminating error occurs, rather than empty arrays. This is normal PowerShell behavior and should be maintained in DSC commands.

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Build Package Module)
🔇 Additional comments (3)
tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1 (1)

1118-1138: LGTM: streamlined DC-object tests and credential path.

Contexts validate found-object and credential usage cleanly; mocks and invocation assertions are correct.

Also applies to: 1140-1166

tests/Unit/MSFT_ADDomainController.Tests.ps1 (1)

66-67: LGTM: switched to OS-level DC check with correct invocation counts.

Mocks and Should -Invoke counts match the new control flow; skipping AD lookups when not a DC is correct.

Also applies to: 88-89, 96-98, 151-152, 196-197, 279-280, 295-296, 328-331

source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (1)

68-75: LGTM: OS-level DC check avoids pre-staged RODC false positives.

This correctly gates AD lookups and resolves issue #747.

Copy link
Contributor Author

@Borgquite Borgquite left a comment

Choose a reason for hiding this comment

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

Reviewable status: 0 of 11 files reviewed, 1 unresolved discussion

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between bc01650 and b22a1f4.

📒 Files selected for processing (3)
  • CHANGELOG.md (1 hunks)
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (6 hunks)
  • tests/Unit/MSFT_ADDomainController.Tests.ps1 (7 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • CHANGELOG.md
🧰 Additional context used
📓 Path-based instructions (5)
**

⚙️ CodeRabbit configuration file

**: # DSC Community Guidelines

Terminology

  • Command: Public command
  • Function: Private function
  • Resource: DSC class-based resource

Build & Test Workflow Requirements

  • Run PowerShell script files from repository root
  • Setup build and test environment (once per pwsh session): ./build.ps1 -Tasks noop
  • Build project before running tests: ./build.ps1 -Tasks build
  • Always run tests in new pwsh session: Invoke-Pester -Path @({test paths}) -Output Detailed

File Organization

  • Public commands: source/Public/{CommandName}.ps1
  • Private functions: source/Private/{FunctionName}.ps1
  • Unit tests: tests/Unit/{Classes|Public|Private}/{Name}.Tests.ps1
  • Integration tests: tests/Integration/Commands/{CommandName}.Integration.Tests.ps1

Requirements

  • Follow instructions over existing code patterns
  • Follow PowerShell style and test guideline instructions strictly
  • Always update CHANGELOG.md Unreleased section
  • Localize all strings using string keys; remove any orphaned string keys
  • Check DscResource.Common before creating private functions
  • Separate reusable logic into private functions
  • DSC resources should always be created as class-based resources
  • Add unit tests for all commands/functions/resources
  • Add integration tests for all public commands and resources

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • tests/Unit/MSFT_ADDomainController.Tests.ps1
{**/*.ps1,**/*.psm1,**/*.psd1}

⚙️ CodeRabbit configuration file

{**/*.ps1,**/*.psm1,**/*.psd1}: # PowerShell Guidelines

Naming

  • Use descriptive names (3+ characters, no abbreviations)
  • Functions: PascalCase with Verb-Noun format using approved verbs
  • Parameters: PascalCase
  • Variables: camelCase
  • Keywords: lower-case
  • Classes: PascalCase
  • Include scope for script/global/environment variables: $script:, $global:, $env:

File naming

  • Class files: ###.ClassName.ps1 format (e.g. 001.SqlReason.ps1, 004.StartupParameters.ps1)

Formatting

Indentation & Spacing

  • Use 4 spaces (no tabs)
  • One space around operators: $a = 1 + 2
  • One space between type and variable: [String] $name
  • One space between keyword and parenthesis: if ($condition)
  • No spaces on empty lines
  • Try to limit lines to 120 characters

Braces

  • Newline before opening brace (except variable assignments)
  • One newline after opening brace
  • Two newlines after closing brace (one if followed by another brace or continuation)

Quotes

  • Use single quotes unless variable expansion is needed: 'text' vs "text $variable"

Arrays

  • Single line: @('one', 'two', 'three')
  • Multi-line: each element on separate line with proper indentation
  • Do not use the unary comma operator (,) in return statements to force
    an array

Hashtables

  • Empty: @{}
  • Each property on separate line with proper indentation
  • Properties: Use PascalCase

Comments

  • Single line: # Comment (capitalized, on own line)
  • Multi-line: <# Comment #> format (opening and closing brackets on own line), and indent text
  • No commented-out code

Comment-based help

  • Always add comment-based help to all functions and scripts
  • Comment-based help: SYNOPSIS, DESCRIPTION (40+ chars), PARAMETER, EXAMPLE sections before function/class
  • Comment-based help indentation: keywords 4 spaces, text 8 spaces
  • Include examples for all parameter sets and combinations
  • INPUTS: List each pipeline‑accepted type (one per line) with a 1‑line description...

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • tests/Unit/MSFT_ADDomainController.Tests.ps1
source/DSCResources/**/*.psm1

⚙️ CodeRabbit configuration file

source/DSCResources/**/*.psm1: # MOF-based Desired State Configuration (DSC) Resources Guidelines

Required Functions

  • Every DSC resource must define: Get-TargetResource, Set-TargetResource, Test-TargetResource
  • Export using *-TargetResource pattern

Function Return Types

  • Get-TargetResource: Must return hashtable with all resource properties
  • Test-TargetResource: Must return boolean ($true/$false)
  • Set-TargetResource: Must not return anything (void)

Parameter Guidelines

  • Get-TargetResource: Only include parameters needed to retrieve actual current state values
  • Get-TargetResource: Remove non-mandatory parameters that are never used
  • Set-TargetResource and Test-TargetResource: Must have identical parameters
  • Set-TargetResource and Test-TargetResource: Unused mandatory parameters: Add "Not used in <function_name>" to help comment

Required Elements

  • Each function must include Write-Verbose at least once
    • Get-TargetResource: Use verbose message starting with "Getting the current state of..."
    • Set-TargetResource: Use verbose message starting with "Setting the desired state of..."
    • Test-TargetResource: Use verbose message starting with "Determining the current state of..."
  • Use localized strings for all messages (Write-Verbose, Write-Error, etc.)
  • Import localized strings using Get-LocalizedData at module top

Error Handling

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
tests/[Uu]nit/**/*.[Tt]ests.ps1

⚙️ CodeRabbit configuration file

tests/[Uu]nit/**/*.[Tt]ests.ps1: # Unit Tests Guidelines

  • Test with localized strings: Use InModuleScope -ScriptBlock { $script:localizedData.Key }
  • Mock files: Use $TestDrive variable (path to the test drive)
  • All public commands require parameter set validation tests
  • After modifying classes, always run tests in new session (for changes to take effect)

Test Setup Requirements

Use this exact setup block before Describe:

[System.Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSUseDeclaredVarsMoreThanAssignments', '', Justification = 'Suppressing this rule because Script Analyzer does not understand Pester syntax.')]
param ()

BeforeDiscovery {
    try
    {
        if (-not (Get-Module -Name 'DscResource.Test'))
        {
            # Assumes dependencies have been resolved, so if this module is not available, run 'noop' task.
            if (-not (Get-Module -Name 'DscResource.Test' -ListAvailable))
            {
                # Redirect all streams to $null, except the error stream (stream 2)
                & "$PSScriptRoot/../../../build.ps1" -Tasks 'noop' 3>&1 4>&1 5>&1 6>&1 > $null
            }

            # If the dependencies have not been resolved, this will throw an error.
            Import-Module -Name 'DscResource.Test' -Force -ErrorAction 'Stop'
        }
    }
    catch [System.IO.FileNotFoundException]
    {
        throw 'DscResource.Test module dependency not found. Please run ".\build.ps1 -ResolveDependency -Tasks noop" first.'
    }
}

BeforeAll {
    $script:moduleName = '{MyModuleName}'

    Import-Module -Name $script:moduleName -Force -ErrorAction 'Stop'

    $PSDefaultParameterValues['InModuleScope:ModuleName'] = $script:moduleName
    $PSDefaultParameterValues['Mock:ModuleName'] = $script:moduleName
    $PSDefaultParameterValues['Should:ModuleName'] = $script:moduleName
}

AfterAll {
    $PSDefaultParameterValues.Remove('InModuleScope:ModuleName')
    $PSDefaultParameterValues.Remove('Mock:ModuleNam...

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
**/*.[Tt]ests.ps1

⚙️ CodeRabbit configuration file

**/*.[Tt]ests.ps1: # Tests Guidelines

Core Requirements

  • All public commands, private functions and classes must have unit tests
  • All public commands and class-based resources must have integration tests
  • Use Pester v5 syntax only
  • Test code only inside Describe blocks
  • Assertions only in It blocks
  • Never test verbose messages, debug messages or parameter binding behavior
  • Pass all mandatory parameters to avoid prompts

Requirements

  • Inside It blocks, assign unused return objects to $null (unless part of pipeline)
  • Tested entity must be called from within the It blocks
  • Keep results and assertions in same It block
  • Avoid try-catch-finally for cleanup, use AfterAll or AfterEach
  • Avoid unnecessary remove/recreate cycles

Naming

  • One Describe block per file matching the tested entity name
  • Context descriptions start with 'When'
  • It descriptions start with 'Should', must not contain 'when'
  • Mock variables prefix: 'mock'

Structure & Scope

  • Public commands: Never use InModuleScope (unless retrieving localized strings)
  • Private functions/class resources: Always use InModuleScope
  • Each class method = separate Context block
  • Each scenario = separate Context block
  • Use nested Context blocks for complex scenarios
  • Mocking in BeforeAll (BeforeEach only when required)
  • Setup/teardown in BeforeAll,BeforeEach/AfterAll,AfterEach close to usage

Syntax Rules

  • PascalCase: Describe, Context, It, Should, BeforeAll, BeforeEach, AfterAll, AfterEach
  • Use -BeTrue/-BeFalse never -Be $true/-Be $false
  • Never use Assert-MockCalled, use Should -Invoke instead
  • No Should -Not -Throw - invoke commands directly
  • Never add an empty -MockWith block
  • Omit -MockWith when returning $null
  • Set $PSDefaultParameterValues for Mock:ModuleName, Should:ModuleName, InModuleScope:ModuleName
  • Omit -ModuleName parameter on Pester commands
  • Never use Mock inside `InModuleSc...

Files:

  • tests/Unit/MSFT_ADDomainController.Tests.ps1
🧠 Learnings (1)
📚 Learning: 2025-08-16T13:35:08.323Z
Learnt from: johlju
PR: dsccommunity/SqlServerDsc#2134
File: source/Public/Get-SqlDscLogin.ps1:0-0
Timestamp: 2025-08-16T13:35:08.323Z
Learning: In PowerShell, users expect to receive $null when no objects are found or when a non-terminating error occurs, rather than empty arrays. This is normal PowerShell behavior and should be maintained in DSC commands.

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Build Package Module)

Copy link

codecov bot commented Oct 2, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 99%. Comparing base (4751ae1) to head (99bc079).

Additional details and impacted files

Impacted file tree graph

@@         Coverage Diff         @@
##           main   #748   +/-   ##
===================================
  Coverage    99%    99%           
===================================
  Files        25     25           
  Lines      3647   3650    +3     
===================================
+ Hits       3620   3623    +3     
  Misses       27     27           
Files with missing lines Coverage Δ
...FT_ADDomainController/MSFT_ADDomainController.psm1 100% <100%> (ø)
...ccount/MSFT_ADReadOnlyDomainControllerAccount.psm1 100% <100%> (ø)
...DirectoryDsc.Common/ActiveDirectoryDsc.Common.psm1 94% <100%> (-1%) ⬇️
🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

Copy link
Contributor Author

@Borgquite Borgquite left a comment

Choose a reason for hiding this comment

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

Reviewable status: 0 of 11 files reviewed, 1 unresolved discussion

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

♻️ Duplicate comments (1)
source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (1)

68-73: Format IsDomainController verbose with both placeholders

String likely expects computer and domain; currently only computer is supplied. Pass DomainName too in both places.

As per coding guidelines

Apply this diff:

-        Write-Verbose -Message ($script:localizedData.IsDomainController -f $env:COMPUTERNAME)
+        Write-Verbose -Message ($script:localizedData.IsDomainController -f $env:COMPUTERNAME, $DomainName)
-        Write-Verbose -Message ($script:localizedData.IsDomainController -f $env:COMPUTERNAME)
+        Write-Verbose -Message ($script:localizedData.IsDomainController -f $env:COMPUTERNAME, $DomainName)

Run to confirm placeholder count in the localized string:

#!/bin/bash
# Find IsDomainController string and show its value to verify placeholder count.
rg -n "IsDomainController" -g "source/**/en-US/*.strings.psd1" -C2

Also applies to: 469-470

🧹 Nitpick comments (5)
tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1 (2)

1118-1138: Tighten success-path assertions; guard against OS-level regression

Assert that Credential is not forwarded and that no OS-level DC check is invoked (ensuring Get-DomainControllerObject stays generic).

 Context 'When domain controller object could be found' {
   BeforeAll {
     Mock -CommandName Get-ADDomainController -MockWith {
       return @{
         Site            = 'MySite'
         Domain          = 'contoso.com'
         IsGlobalCatalog = $true
       }
     }
+    # Guard: ensure Get-DomainControllerObject doesn't rely on OS-level checks
+    Mock -CommandName Test-IsDomainController
   }

   It 'Should return the correct values for each property' {
     $getDomainControllerObjectResult = Get-DomainControllerObject -DomainName 'contoso.com'

     $getDomainControllerObjectResult.Site | Should -Be 'MySite'
     $getDomainControllerObjectResult.Domain | Should -Be 'contoso.com'
     $getDomainControllerObjectResult.IsGlobalCatalog | Should -BeTrue

-    Should -Invoke -CommandName Get-ADDomainController -Exactly -Times 1 -Scope It
+    Should -Invoke -CommandName Get-ADDomainController -ParameterFilter {
+        -not $PesterBoundParameters.ContainsKey('Credential')
+    } -Exactly -Times 1 -Scope It
+    Should -Invoke -CommandName Test-IsDomainController -Exactly -Times 0 -Scope It
   }
 }

1140-1166: Verify credential pass-through and absence of OS-level checks

Keep the existing credential check, and add a regression guard so OS-level DC checks aren’t reintroduced.

 Context 'When domain controller object could be found, using specific credential' {
   BeforeAll {
     Mock -CommandName Get-ADDomainController -MockWith {
       return @{
         Site            = 'MySite'
         Domain          = 'contoso.com'
         IsGlobalCatalog = $true
       }
     }
+    # Guard: ensure Get-DomainControllerObject doesn't rely on OS-level checks
+    Mock -CommandName Test-IsDomainController

     $mockAdministratorUser = 'admin@contoso.com'
     $mockAdministratorPassword = 'P@ssw0rd-12P@ssw0rd-12' | ConvertTo-SecureString -AsPlainText -Force
     $mockAdministratorCredential = New-Object -TypeName 'System.Management.Automation.PSCredential' -ArgumentList @($mockAdministratorUser, $mockAdministratorPassword)
   }

   It 'Should return the correct values for each property' {
     $getDomainControllerObjectResult = Get-DomainControllerObject -DomainName 'contoso.com' -Credential $mockAdministratorCredential

     $getDomainControllerObjectResult.Site | Should -Be 'MySite'
     $getDomainControllerObjectResult.Domain | Should -Be 'contoso.com'
     $getDomainControllerObjectResult.IsGlobalCatalog | Should -BeTrue

     Should -Invoke -CommandName Get-ADDomainController -ParameterFilter {
       $PesterBoundParameters.ContainsKey('Credential') -eq $true
     } -Exactly -Times 1 -Scope It
+    Should -Invoke -CommandName Test-IsDomainController -Exactly -Times 0 -Scope It
   }
 }
source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (2)

32-42: Sync “Used Functions” list with actual calls

Get-TargetResource calls Get-DomainObject but the list doesn’t include it; it lists Get-ADDomain which isn’t used here.

As per coding guidelines

Suggested edit:

-            Get-ADDomain                                    | ActiveDirectory
+            Get-DomainObject                                 | ActiveDirectoryDsc.Common

84-86: Avoid backticks and implicit pipeline identities

Backticks aren’t recommended; also prefer explicit -Identity over piping DN/objects into AD cmdlets for clarity.

As per coding guidelines

Example refactor:

-$domainControllerObject = Get-DomainControllerObject `
-    -DomainName $DomainName -ComputerName $env:COMPUTERNAME -Credential $Credential
+$domainControllerObject = Get-DomainControllerObject -DomainName $DomainName -ComputerName $env:COMPUTERNAME -Credential $Credential
-$domainControllerComputerObject = $domainControllerObject.ComputerObjectDN |
-    Get-ADComputer -Properties ManagedBy -Credential $Credential
+$domainControllerComputerObject = Get-ADComputer -Identity $domainControllerObject.ComputerObjectDN -Properties ManagedBy -Credential $Credential
-$domainControllerManagedByObject = $domainControllerComputerObject.ManagedBy |
-    Get-ADObject -Properties objectSid -Credential $Credential
+$domainControllerManagedByObject = Get-ADObject -Identity $domainControllerComputerObject.ManagedBy -Properties objectSid -Credential $Credential

Also applies to: 98-103

tests/Unit/MSFT_ADDomainController.Tests.ps1 (1)

1137-1153: Consider phasing out “Should -Not -Throw”

Guidelines recommend invoking commands directly instead of asserting “-Not -Throw.” Adopt over time to reduce noise and align with repo standards.

As per coding guidelines

Also applies to: 1156-1172, 1175-1191, 1194-1210, 1237-1253, 1274-1291, 1293-1310, 1312-1329, 1331-1349, 1352-1370, 1373-1391, 1394-1412, 1415-1433, 1436-1452, 1455-1471, 1493-1507, 1550-1566, 1579-1594, 1610-1626, 1653-1676, 1696-1714, 1734-1752, 1779-1796, 1823-1840, 1865-1880, 1904-1919, 1933-1948, 1962-1977, 2005-2023, 2043-2061, 2074-2092

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between b22a1f4 and 428977d.

📒 Files selected for processing (4)
  • CHANGELOG.md (1 hunks)
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (7 hunks)
  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1 (2 hunks)
  • tests/Unit/MSFT_ADDomainController.Tests.ps1 (7 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • CHANGELOG.md
🧰 Additional context used
📓 Path-based instructions (5)
**

⚙️ CodeRabbit configuration file

**: # DSC Community Guidelines

Terminology

  • Command: Public command
  • Function: Private function
  • Resource: DSC class-based resource

Build & Test Workflow Requirements

  • Run PowerShell script files from repository root
  • Setup build and test environment (once per pwsh session): ./build.ps1 -Tasks noop
  • Build project before running tests: ./build.ps1 -Tasks build
  • Always run tests in new pwsh session: Invoke-Pester -Path @({test paths}) -Output Detailed

File Organization

  • Public commands: source/Public/{CommandName}.ps1
  • Private functions: source/Private/{FunctionName}.ps1
  • Unit tests: tests/Unit/{Classes|Public|Private}/{Name}.Tests.ps1
  • Integration tests: tests/Integration/Commands/{CommandName}.Integration.Tests.ps1

Requirements

  • Follow instructions over existing code patterns
  • Follow PowerShell style and test guideline instructions strictly
  • Always update CHANGELOG.md Unreleased section
  • Localize all strings using string keys; remove any orphaned string keys
  • Check DscResource.Common before creating private functions
  • Separate reusable logic into private functions
  • DSC resources should always be created as class-based resources
  • Add unit tests for all commands/functions/resources
  • Add integration tests for all public commands and resources

Files:

  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • tests/Unit/MSFT_ADDomainController.Tests.ps1
tests/[Uu]nit/**/*.[Tt]ests.ps1

⚙️ CodeRabbit configuration file

tests/[Uu]nit/**/*.[Tt]ests.ps1: # Unit Tests Guidelines

  • Test with localized strings: Use InModuleScope -ScriptBlock { $script:localizedData.Key }
  • Mock files: Use $TestDrive variable (path to the test drive)
  • All public commands require parameter set validation tests
  • After modifying classes, always run tests in new session (for changes to take effect)

Test Setup Requirements

Use this exact setup block before Describe:

[System.Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSUseDeclaredVarsMoreThanAssignments', '', Justification = 'Suppressing this rule because Script Analyzer does not understand Pester syntax.')]
param ()

BeforeDiscovery {
    try
    {
        if (-not (Get-Module -Name 'DscResource.Test'))
        {
            # Assumes dependencies have been resolved, so if this module is not available, run 'noop' task.
            if (-not (Get-Module -Name 'DscResource.Test' -ListAvailable))
            {
                # Redirect all streams to $null, except the error stream (stream 2)
                & "$PSScriptRoot/../../../build.ps1" -Tasks 'noop' 3>&1 4>&1 5>&1 6>&1 > $null
            }

            # If the dependencies have not been resolved, this will throw an error.
            Import-Module -Name 'DscResource.Test' -Force -ErrorAction 'Stop'
        }
    }
    catch [System.IO.FileNotFoundException]
    {
        throw 'DscResource.Test module dependency not found. Please run ".\build.ps1 -ResolveDependency -Tasks noop" first.'
    }
}

BeforeAll {
    $script:moduleName = '{MyModuleName}'

    Import-Module -Name $script:moduleName -Force -ErrorAction 'Stop'

    $PSDefaultParameterValues['InModuleScope:ModuleName'] = $script:moduleName
    $PSDefaultParameterValues['Mock:ModuleName'] = $script:moduleName
    $PSDefaultParameterValues['Should:ModuleName'] = $script:moduleName
}

AfterAll {
    $PSDefaultParameterValues.Remove('InModuleScope:ModuleName')
    $PSDefaultParameterValues.Remove('Mock:ModuleNam...

Files:

  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
  • tests/Unit/MSFT_ADDomainController.Tests.ps1
{**/*.ps1,**/*.psm1,**/*.psd1}

⚙️ CodeRabbit configuration file

{**/*.ps1,**/*.psm1,**/*.psd1}: # PowerShell Guidelines

Naming

  • Use descriptive names (3+ characters, no abbreviations)
  • Functions: PascalCase with Verb-Noun format using approved verbs
  • Parameters: PascalCase
  • Variables: camelCase
  • Keywords: lower-case
  • Classes: PascalCase
  • Include scope for script/global/environment variables: $script:, $global:, $env:

File naming

  • Class files: ###.ClassName.ps1 format (e.g. 001.SqlReason.ps1, 004.StartupParameters.ps1)

Formatting

Indentation & Spacing

  • Use 4 spaces (no tabs)
  • One space around operators: $a = 1 + 2
  • One space between type and variable: [String] $name
  • One space between keyword and parenthesis: if ($condition)
  • No spaces on empty lines
  • Try to limit lines to 120 characters

Braces

  • Newline before opening brace (except variable assignments)
  • One newline after opening brace
  • Two newlines after closing brace (one if followed by another brace or continuation)

Quotes

  • Use single quotes unless variable expansion is needed: 'text' vs "text $variable"

Arrays

  • Single line: @('one', 'two', 'three')
  • Multi-line: each element on separate line with proper indentation
  • Do not use the unary comma operator (,) in return statements to force
    an array

Hashtables

  • Empty: @{}
  • Each property on separate line with proper indentation
  • Properties: Use PascalCase

Comments

  • Single line: # Comment (capitalized, on own line)
  • Multi-line: <# Comment #> format (opening and closing brackets on own line), and indent text
  • No commented-out code

Comment-based help

  • Always add comment-based help to all functions and scripts
  • Comment-based help: SYNOPSIS, DESCRIPTION (40+ chars), PARAMETER, EXAMPLE sections before function/class
  • Comment-based help indentation: keywords 4 spaces, text 8 spaces
  • Include examples for all parameter sets and combinations
  • INPUTS: List each pipeline‑accepted type (one per line) with a 1‑line description...

Files:

  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
  • tests/Unit/MSFT_ADDomainController.Tests.ps1
**/*.[Tt]ests.ps1

⚙️ CodeRabbit configuration file

**/*.[Tt]ests.ps1: # Tests Guidelines

Core Requirements

  • All public commands, private functions and classes must have unit tests
  • All public commands and class-based resources must have integration tests
  • Use Pester v5 syntax only
  • Test code only inside Describe blocks
  • Assertions only in It blocks
  • Never test verbose messages, debug messages or parameter binding behavior
  • Pass all mandatory parameters to avoid prompts

Requirements

  • Inside It blocks, assign unused return objects to $null (unless part of pipeline)
  • Tested entity must be called from within the It blocks
  • Keep results and assertions in same It block
  • Avoid try-catch-finally for cleanup, use AfterAll or AfterEach
  • Avoid unnecessary remove/recreate cycles

Naming

  • One Describe block per file matching the tested entity name
  • Context descriptions start with 'When'
  • It descriptions start with 'Should', must not contain 'when'
  • Mock variables prefix: 'mock'

Structure & Scope

  • Public commands: Never use InModuleScope (unless retrieving localized strings)
  • Private functions/class resources: Always use InModuleScope
  • Each class method = separate Context block
  • Each scenario = separate Context block
  • Use nested Context blocks for complex scenarios
  • Mocking in BeforeAll (BeforeEach only when required)
  • Setup/teardown in BeforeAll,BeforeEach/AfterAll,AfterEach close to usage

Syntax Rules

  • PascalCase: Describe, Context, It, Should, BeforeAll, BeforeEach, AfterAll, AfterEach
  • Use -BeTrue/-BeFalse never -Be $true/-Be $false
  • Never use Assert-MockCalled, use Should -Invoke instead
  • No Should -Not -Throw - invoke commands directly
  • Never add an empty -MockWith block
  • Omit -MockWith when returning $null
  • Set $PSDefaultParameterValues for Mock:ModuleName, Should:ModuleName, InModuleScope:ModuleName
  • Omit -ModuleName parameter on Pester commands
  • Never use Mock inside `InModuleSc...

Files:

  • tests/Unit/ActiveDirectoryDsc.Common/ActiveDirectoryDsc.Common.Tests.ps1
  • tests/Unit/MSFT_ADDomainController.Tests.ps1
source/DSCResources/**/*.psm1

⚙️ CodeRabbit configuration file

source/DSCResources/**/*.psm1: # MOF-based Desired State Configuration (DSC) Resources Guidelines

Required Functions

  • Every DSC resource must define: Get-TargetResource, Set-TargetResource, Test-TargetResource
  • Export using *-TargetResource pattern

Function Return Types

  • Get-TargetResource: Must return hashtable with all resource properties
  • Test-TargetResource: Must return boolean ($true/$false)
  • Set-TargetResource: Must not return anything (void)

Parameter Guidelines

  • Get-TargetResource: Only include parameters needed to retrieve actual current state values
  • Get-TargetResource: Remove non-mandatory parameters that are never used
  • Set-TargetResource and Test-TargetResource: Must have identical parameters
  • Set-TargetResource and Test-TargetResource: Unused mandatory parameters: Add "Not used in <function_name>" to help comment

Required Elements

  • Each function must include Write-Verbose at least once
    • Get-TargetResource: Use verbose message starting with "Getting the current state of..."
    • Set-TargetResource: Use verbose message starting with "Setting the desired state of..."
    • Test-TargetResource: Use verbose message starting with "Determining the current state of..."
  • Use localized strings for all messages (Write-Verbose, Write-Error, etc.)
  • Import localized strings using Get-LocalizedData at module top

Error Handling

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
🧠 Learnings (4)
📚 Learning: 2025-08-16T13:35:08.323Z
Learnt from: johlju
PR: dsccommunity/SqlServerDsc#2134
File: source/Public/Get-SqlDscLogin.ps1:0-0
Timestamp: 2025-08-16T13:35:08.323Z
Learning: In PowerShell, users expect to receive $null when no objects are found or when a non-terminating error occurs, rather than empty arrays. This is normal PowerShell behavior and should be maintained in DSC commands.

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
📚 Learning: 2025-08-29T17:22:23.268Z
Learnt from: CR
PR: dsccommunity/SqlServerDsc#0
File: .github/instructions/dsc-community-style-guidelines-localization.instructions.md:0-0
Timestamp: 2025-08-29T17:22:23.268Z
Learning: Applies to source/**/*.ps1 : When emitting messages, reference $script:localizedData.KeyName and format with the -f operator (e.g., Write-Verbose -Message ($script:localizedData.KeyName -f $value1))

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
📚 Learning: 2025-09-12T13:20:57.155Z
Learnt from: CR
PR: dsccommunity/SqlServerDsc#0
File: .github/instructions/dsc-community-style-guidelines-mof-resources.instructions.md:0-0
Timestamp: 2025-09-12T13:20:57.155Z
Learning: Applies to source/DSCResources/**/*.psm1 : Use localized strings for all messages (e.g., Write-Verbose, Write-Error)

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
📚 Learning: 2025-08-17T10:48:15.384Z
Learnt from: johlju
PR: dsccommunity/SqlServerDsc#2136
File: source/suffix.ps1:24-24
Timestamp: 2025-08-17T10:48:15.384Z
Learning: In source/suffix.ps1, the Write-Verbose message in the catch block for Import-SqlDscPreferredModule does not need localization because the exception message from Import-SqlDscPreferredModule is already localized by that command, making it an edge case exception to the localization guidelines.

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: dsccommunity.ActiveDirectoryDsc (Build Package Module)
🔇 Additional comments (2)
source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (1)

92-112: Good null-guards around RODC delegated admin resolution

Checks for ComputerObjectDN, ManagedBy, and objectSid prevent pipeline/property errors. Nicely hardened.

Based on learnings

tests/Unit/MSFT_ADDomainController.Tests.ps1 (1)

63-90: Tests correctly model the OS-level DC check

Mocks and Should -Invoke counts for Test-IsDomainController are spot on and validate the new control flow paths.

Also applies to: 92-120, 147-188, 190-233, 235-319, 321-367

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (2)
source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (2)

82-84: Avoid backticks; use splatting and Get-ComputerName

Backticks are discouraged. Also prefer Get-ComputerName over $env:COMPUTERNAME (per guidelines, DscResource.Common is already imported).

-        $domainControllerObject = Get-DomainControllerObject `
-            -DomainName $DomainName -ComputerName $env:COMPUTERNAME -Credential $Credential
+        $getDomainControllerObjectParams = @{
+            DomainName   = $DomainName
+            ComputerName = Get-ComputerName
+            Credential   = $Credential
+        }
+        $domainControllerObject = Get-DomainControllerObject @getDomainControllerObjectParams

As per coding guidelines


467-467: Prefer Get-ComputerName in verbose message

Replace $env:COMPUTERNAME for cross‑platform correctness.

-        Write-Verbose -Message ($script:localizedData.IsDomainControllerInDomain -f $env:COMPUTERNAME, $DomainName)
+        Write-Verbose -Message ($script:localizedData.IsDomainControllerInDomain -f (Get-ComputerName), $DomainName)

As per coding guidelines

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 428977d and 93cc007.

📒 Files selected for processing (2)
  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (7 hunks)
  • source/DSCResources/MSFT_ADDomainController/en-US/MSFT_ADDomainController.strings.psd1 (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • source/DSCResources/MSFT_ADDomainController/en-US/MSFT_ADDomainController.strings.psd1
🧰 Additional context used
📓 Path-based instructions (3)
**

⚙️ CodeRabbit configuration file

**: # DSC Community Guidelines

Terminology

  • Command: Public command
  • Function: Private function
  • Resource: DSC class-based resource

Build & Test Workflow Requirements

  • Run PowerShell script files from repository root
  • Setup build and test environment (once per pwsh session): ./build.ps1 -Tasks noop
  • Build project before running tests: ./build.ps1 -Tasks build
  • Always run tests in new pwsh session: Invoke-Pester -Path @({test paths}) -Output Detailed

File Organization

  • Public commands: source/Public/{CommandName}.ps1
  • Private functions: source/Private/{FunctionName}.ps1
  • Unit tests: tests/Unit/{Classes|Public|Private}/{Name}.Tests.ps1
  • Integration tests: tests/Integration/Commands/{CommandName}.Integration.Tests.ps1

Requirements

  • Follow instructions over existing code patterns
  • Follow PowerShell style and test guideline instructions strictly
  • Always update CHANGELOG.md Unreleased section
  • Localize all strings using string keys; remove any orphaned string keys
  • Check DscResource.Common before creating private functions
  • Separate reusable logic into private functions
  • DSC resources should always be created as class-based resources
  • Add unit tests for all commands/functions/resources
  • Add integration tests for all public commands and resources

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
{**/*.ps1,**/*.psm1,**/*.psd1}

⚙️ CodeRabbit configuration file

{**/*.ps1,**/*.psm1,**/*.psd1}: # PowerShell Guidelines

Naming

  • Use descriptive names (3+ characters, no abbreviations)
  • Functions: PascalCase with Verb-Noun format using approved verbs
  • Parameters: PascalCase
  • Variables: camelCase
  • Keywords: lower-case
  • Classes: PascalCase
  • Include scope for script/global/environment variables: $script:, $global:, $env:

File naming

  • Class files: ###.ClassName.ps1 format (e.g. 001.SqlReason.ps1, 004.StartupParameters.ps1)

Formatting

Indentation & Spacing

  • Use 4 spaces (no tabs)
  • One space around operators: $a = 1 + 2
  • One space between type and variable: [String] $name
  • One space between keyword and parenthesis: if ($condition)
  • No spaces on empty lines
  • Try to limit lines to 120 characters

Braces

  • Newline before opening brace (except variable assignments)
  • One newline after opening brace
  • Two newlines after closing brace (one if followed by another brace or continuation)

Quotes

  • Use single quotes unless variable expansion is needed: 'text' vs "text $variable"

Arrays

  • Single line: @('one', 'two', 'three')
  • Multi-line: each element on separate line with proper indentation
  • Do not use the unary comma operator (,) in return statements to force
    an array

Hashtables

  • Empty: @{}
  • Each property on separate line with proper indentation
  • Properties: Use PascalCase

Comments

  • Single line: # Comment (capitalized, on own line)
  • Multi-line: <# Comment #> format (opening and closing brackets on own line), and indent text
  • No commented-out code

Comment-based help

  • Always add comment-based help to all functions and scripts
  • Comment-based help: SYNOPSIS, DESCRIPTION (40+ chars), PARAMETER, EXAMPLE sections before function/class
  • Comment-based help indentation: keywords 4 spaces, text 8 spaces
  • Include examples for all parameter sets and combinations
  • INPUTS: List each pipeline‑accepted type (one per line) with a 1‑line description...

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
source/DSCResources/**/*.psm1

⚙️ CodeRabbit configuration file

source/DSCResources/**/*.psm1: # MOF-based Desired State Configuration (DSC) Resources Guidelines

Required Functions

  • Every DSC resource must define: Get-TargetResource, Set-TargetResource, Test-TargetResource
  • Export using *-TargetResource pattern

Function Return Types

  • Get-TargetResource: Must return hashtable with all resource properties
  • Test-TargetResource: Must return boolean ($true/$false)
  • Set-TargetResource: Must not return anything (void)

Parameter Guidelines

  • Get-TargetResource: Only include parameters needed to retrieve actual current state values
  • Get-TargetResource: Remove non-mandatory parameters that are never used
  • Set-TargetResource and Test-TargetResource: Must have identical parameters
  • Set-TargetResource and Test-TargetResource: Unused mandatory parameters: Add "Not used in <function_name>" to help comment

Required Elements

  • Each function must include Write-Verbose at least once
    • Get-TargetResource: Use verbose message starting with "Getting the current state of..."
    • Set-TargetResource: Use verbose message starting with "Setting the desired state of..."
    • Test-TargetResource: Use verbose message starting with "Determining the current state of..."
  • Use localized strings for all messages (Write-Verbose, Write-Error, etc.)
  • Import localized strings using Get-LocalizedData at module top

Error Handling

Files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
🧠 Learnings (4)
📚 Learning: 2025-08-16T13:35:08.323Z
Learnt from: johlju
PR: dsccommunity/SqlServerDsc#2134
File: source/Public/Get-SqlDscLogin.ps1:0-0
Timestamp: 2025-08-16T13:35:08.323Z
Learning: In PowerShell, users expect to receive $null when no objects are found or when a non-terminating error occurs, rather than empty arrays. This is normal PowerShell behavior and should be maintained in DSC commands.

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
📚 Learning: 2025-08-29T17:22:23.268Z
Learnt from: CR
PR: dsccommunity/SqlServerDsc#0
File: .github/instructions/dsc-community-style-guidelines-localization.instructions.md:0-0
Timestamp: 2025-08-29T17:22:23.268Z
Learning: Applies to source/**/*.ps1 : When emitting messages, reference $script:localizedData.KeyName and format with the -f operator (e.g., Write-Verbose -Message ($script:localizedData.KeyName -f $value1))

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
📚 Learning: 2025-09-12T13:20:57.155Z
Learnt from: CR
PR: dsccommunity/SqlServerDsc#0
File: .github/instructions/dsc-community-style-guidelines-mof-resources.instructions.md:0-0
Timestamp: 2025-09-12T13:20:57.155Z
Learning: Applies to source/DSCResources/**/*.psm1 : Use localized strings for all messages (e.g., Write-Verbose, Write-Error)

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
📚 Learning: 2025-08-17T10:48:15.384Z
Learnt from: johlju
PR: dsccommunity/SqlServerDsc#2136
File: source/suffix.ps1:24-24
Timestamp: 2025-08-17T10:48:15.384Z
Learning: In source/suffix.ps1, the Write-Verbose message in the catch block for Import-SqlDscPreferredModule does not need localization because the exception message from Import-SqlDscPreferredModule is already localized by that command, making it an edge case exception to the localization guidelines.

Applied to files:

  • source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1
🔇 Additional comments (5)
source/DSCResources/MSFT_ADDomainController/MSFT_ADDomainController.psm1 (5)

68-81: Good: OS-level DC check before AD queries

This fixes the pre-staged RODC false-positive by gating on actual OS DC state. No issues.


90-110: Delegated admin resolution now defensively guarded

Null checks for ComputerObjectDN, ManagedBy, and objectSid look correct and prevent pipeline errors. LGTM.


112-121: Replication policy and service/registry reads

Looks correct and idempotent; array casts are handled later. No changes needed.


122-141: Target hashtable assembly

Properties and types look consistent; wrapping lists with @() ensures stable array types. LGTM.


513-517: No change needed for ManagedBy parameter
Set-ADComputer -ManagedBy accepts SID strings (objectSid), so using Resolve-SecurityIdentifier is valid.

@Borgquite Borgquite marked this pull request as ready for review October 2, 2025 16:11
@Borgquite
Copy link
Contributor Author

@johlju Sorry know you're ultra-busy - if you did get a chance to merge this would really help as can't deploy any RODCs in our environment at present :)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

1 participant