Cherry picking computers from AD

Microsoft Windows
Post Reply
User avatar
MigrationUser
Posts: 336
Joined: 2021-Jul-12, 1:37 pm
Contact:

Cherry picking computers from AD

Post by MigrationUser »

19 Jun 2011 05:03
GrendelPrime

I'm looking for a way to parse the computer names in Active Directory to only hit on names that follow the naming convention of POS###REG##, so that I can direct the next step of the batch to them but leave all others alone.

So far I have;
dsquery computer domainroot -name MPOS***REG** -limit 500
which gives me all the computer names I'm looking for.

My next step is to have each query response used as the target for my .bat that sends it our .exe and creates a scheduled task to run the .exe nightly.

I have started reading up on using FOR /F, and will keep plugging away, but any guidance or assistance would be appreciated.

----------------------------

#2 19 Jun 2011 12:26
Simon Sheppard


One way would be to run a vbscript to drop the relevant computernames into a text file, and then read them back in with a FOR loop

The example below can be modified to run wildcard queries against AD
https://ss64.com/vb/syntax-ad.html

----------------------------

#3 19 Jun 2011 15:02
RG


I just have my Home Vista PC here, so can't actually try this till at work tomorrow. If you prefer to do this strictly from bat you should be able to do so. Take a look at the FIND and FINDSTR commands. You can 'pipe' the output of your command to FINDSTR and/or FIND. Start with something like:

Code: Select all

dsquery computer domainroot -name MPOS***REG** -limit 500 | findstr /b "POS"
That means, pipe the output of you command into FINDSTR and display only those lines that start with POS.
Do FINDSTR /? to see numerous options you may or may not want to use with FINDSTR.
If you need to further discriminate you can pipe all of that to another FIND or FINDSTR like the line below, which means that the line has to start with "POS" AND has to include REG:

Code: Select all

dsquery computer domainroot -name MPOS***REG** -limit 500 | findstr /b "POS" | find "REG"
If you need to exclude lines that contain a string you can do that like this:

Code: Select all

dsquery computer domainroot -name MPOS***REG** -limit 500 | findstr /b "POS" | find "REG" | find /v "YourExcludeString"
Let us know how your doing. Post a few lines of your dsquery results and somebody will help you get it working.

Windows Shell Scripting and InstallShield

----------------------------

#4 20 Jun 2011 01:18
GrendelPrime


Thus far...

C:\>dsquery computer domainroot -name MPOS***REG** -limit 500

"CN=MPOS201REG01,CN=Computers,DC=use,DC=oregon,DC=org"
"CN=MPOS201REG02,OU=Merchandise,OU=POS Registers,OU=Domain Computers,DC=use,DC=oregon,DC=org"
"CN=MPOS201REG03,OU=Merchandise,OU=POS Registers,OU=Domain Computers,DC=use,DC=oregon,DC=org"
<snip>

------------------------------------------------------------

C:\>dsquery computer domainroot -name MPOS***REG** -limit 500 | findstr /b "MPOS"

C:\>

Looks like the CN= is throwing off the /b.
------------------------------------------------------------

C:\>dsquery computer domainroot -name MPOS***REG** -limit 500 | findstr "MPOS[class0-9]"

"CN=MPOS201REG01,CN=Computers,DC=use,DC=oregon,DC=org"
"CN=MPOS201REG02,OU=Merchandise,OU=POS Registers,OU=Domain Computers,DC=use,DC=oregon,DC=org"
"CN=MPOS201REG03,OU=Merchandise,OU=POS Registers,OU=Domain Computers,DC=use,DC=oregon,DC=org"
<snip>

Adding the [class] notation filtered out a few non-standard named machines. MPOSTRAININGREG for example
------------------------------------------------------------

Desired output would be;
"MPOS201REG01"
"MPOS201REG02"
"MPOS201REG03"
<snip>


After identifying all the target machines, hopefully FOR /F can be convinced to let me copy my file to each computer that matches.

So much to learn... smile

Last edited by GrendelPrime (20 Jun 2011 02:33)

----------------------------

#5 20 Jun 2011 03:14
RG


You are right. With those results we don't want the /B
Now we will use a for loop to remove everthing from the = left and from the , right. So "delims==," will specify that the = and the , are delimiters. "tokens=2" indicates we want the 2nd token. Also note that we now need to escape the | with a ^ when we use the | this way. The following line should produce the results you want.

Code: Select all

for /f "usebackq tokens=2 delims==," %%a in (`dsquery computer domainroot -name MPOS***REG** -limit 500 ^| findstr "MPOS[class0-9]"`) do (
   echo.%%a
   REM add your command here to copy file to %%a later after you verify that proper results are displayed
)
Untested.

Windows Shell Scripting and InstallShield

----------------------------

#6 20 Jun 2011 04:18
GrendelPrime


That FOR /F gave me exactly the format I was aiming for, the results can be append into a text file to be called by another batch, so it's technically working, but I like the idea of a single batch file to do the whole job.

Addressing a machine as \\%%a to copy the payload isn't going to work, though %%a does echo as the computer name.

Is there a way to use a variable as the destination for a copy command?

----------------------------

#7 20 Jun 2011 11:56
RG


I agree that it would be nice to have it all in one batch file and that certainly is feasible.
I don't understand your statement "Addressing a machine as \\%%a to copy the payload isn't going to work, though %%a does echo as the computer name."
Are you sure that you are using %%a within the parens as shown in my last post? %%a is only valid within the FOR statement. We could set a variable = %%a, but then when we got out of the loop the variable would be set to the last value in the list (can be handy at times, but not this time).
You will need to use quotes if you are using a destination like
"\\%%a\Some Folder\My File"

Last edited by RG (20 Jun 2011 12:17)

Windows Shell Scripting and InstallShield

----------------------------

#8 20 Jun 2011 17:47
GrendelPrime


There is the blind spot I was looking for, I wasn't wrapping the argument in quotes!

I'll make that correction when I get to the office tonight and test it out.
I already owe you a beer, but if this works, I'll make it an import! big_smile

----------------------------

#9 20 Jun 2011 23:34
GrendelPrime


Qapla'!

beer_chug.gif

Just had it copy a 10B txt file to test, but worked perfectly!

Code: Select all

for /f "usebackq tokens=2 delims==," %%a in (`dsquery computer domainroot -name MPOS***REG** -limit 500 ^| findstr "MPOS[class0-9]"`) do ( copy c:\test.txt "\\%%a\c$" )
I'll update to copy the actual file and pipe in the AT command to schedule the task and may add a filter to ping the name first and skip over it if there's no response (waiting for unresponsive machines to timeout makes the script take a long time to run).

Why can't I just leave a working script alone? :wall:

----------------------------

#10 21 Jun 2011 02:39
RG


Great, looks like you have things well under control!
Thanks for sharing a beer!
What country are you sending that import from? smile

Windows Shell Scripting and InstallShield
Post Reply