Posted in ActiveDirectory, Powershell

Leaves or not – Removing an AD Computer Object

I read two posts  recently about removing computers from AD, specifically Computers with leaf objects. A computer can have leaf objects for several things, as an example a PrintServer has leaf objects for each Print Queue. I remember coming into the issue with leaf objects in the past. Blindly using Remove-ADObject can be problematic as was mentioned in one of the posts I was reading. If you have ever run a Remove-ADcomputer and received an error you may have just went into AD Computers and Users and just deleted … ugggh lots of mouse clicking.

I took this as a chance to just write a quick piece of PowerShell code that might provide  a better way to handle this. I took a chuck of code which was part of a ForEach loop just to provide a simple one-for-one you can use with which you can test and have some peace of mind.


$testCase = Get-ADComputer somecomputername
$leafObjects = get-ADObject -Filter * -SearchBase $testCase.DistinguishedName
If ($leafObjects.count -gt 0) {
# Leaf objects involved so Remove-ADObject
"Removing $(testCase.Name) with Remove-ADObject"
Remove-ADObject $testCase.DistinguishedName -Recursive -Confirm:$False -Force
}
Else {
# No leaf objects found so we can use the Computer specific method
"Removing $(testCase.Name) with Remove-ADComputer"
$testCase | Remove-ADComputer -Confirm:$False -Force
}

Again this was just some code I scratchpad-ed, any feedback is welcome.

Getting PowerShell Code into a WordPress.com post is just a pain…. where are my tabs? even if I precede indented text with four spaces

Posted in ActiveDirectory, CLI, Powershell

Get-ACL for a Computer Object

Just a quick post as I ran into something that really had me confused.  I have used get-acl and set-acl for folders and files, very frequently and easily actually.  Researching an SCCM issue, a scripting task presented itself.  A list of all computers and whether or not the “Windows Authorization Access Group” is listed in the Security for the object.  Using AD Users and Computers, you have to use View\Advanced Features, and then inspect the Security tab for the computer object.  I wrote a quick loop and on one machine it was producing verifiable results while on another machine the results were consistently negative results.

Versions of Powershell are the same, the ActiveDirectory module is the same… hmmmmm what is the difference?  “pwd” revealed the culprit.  What is odd, with my other ACL operations I did not specifiy that the current location is AD:\ but in order for get-acl $machine.DistinguishedName  to work and not return object not found I have to ensure get-location returns AD:\

Posted in ActiveDirectory, Powershell, Regex

RegEx for dates

So I am glad to be back into a position where I can freely use Powershell again (still amazes me the Windows shops who frown upon “working” on code). Working on a project where original estimates said it couldn’t be done, simply because timestamps being written were mixed with text, basically a label.

In short, a process to update ActiveDirectory with an external source updates a custom attribute field with a label and then a datetime stamp. I knew RegEx was the way but forming a valid RegEx was the first hurdle. With some research and then some validation tools I came up with the pattern I needed to use.

   1: $regex = "(?=\d)(?:(?:(?:(?:(?:0?[13578]|1[02])(\/|-|\.)31)\1|(?:(?:0?[1,3-9]|1[0-2])(\/|-|\.)(?:29|30)\2))(?:(?:1[6-9]|[2-9]\d)?\d{2})|(?:0?2(\/|-|\.)29\3(?:(?:(?:1[6-9]|[2-9]\d)?(?:0[48]|[2468][048]|[13579][26])|(?:(?:16|[2468][048]|[3579][26])00))))|(?:(?:0?[1-9])|(?:1[0-2]))(\/|-|\.)(?:0?[1-9]|1\d|2[0-8])\4(?:(?:1[6-9]|[2-9]\d)?\d{2}))($|\ (?=\d)))?(((0?[1-9]|1[012])(:[0-5]\d){0,2}(\ [AP]M))|([01]\d|2[0-3])(:[0-5]\d){1,2})?$"

So then I started to play with it, I knew I had to use –match but getting a return value of True wasn’t what I was looking for. The reason I am posting this is for anyone else who threw up their hands on how to use RegEx in Powershell. The trick is –match not only returns True/False, it returns values into a variable name matches ($matches). Now you can interrogate $matches and get the value you were originally targeting. In my case it went something like…

   1: if ($var.extensionAttribute14 -match $regex){

   2:         $ultidate = get-date($matches[0])

   3: }

.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, “Courier New”, courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

By evaluating the string within the AD extensionAttribute it finds the date string and stores just that value in a variable where I can perform date oriented comparisons and ultimately only return records where the update has been recent.

.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, “Courier New”, courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }Preferred Powershell Editor

(polls)