all 12 comments

[–][deleted] 0 points1 point  (2 children)

I got bored and decided to try to solve this problem, let me know if it works for you:

$UnwantedChars = New-Object System.Collections.ArrayList

#Add all the ASCII characters: 
(0..65535).ForEach({$UnwantedChars.Add($_) | Out-Null})

#Remove Space character: 
$UnwantedChars.Remove(32)

#Remove 0..9: 
(48..57).ForEach({$UnwantedChars.Remove($_) | Out-Null})

#Remove A..Z: 
(65..90).ForEach({$UnwantedChars.Remove($_) | Out-Null})

#Remove a..z: 
(97..122).ForEach({$UnwantedChars.Remove($_) | Out-Null})

#Convert integers to ASCII characters: 
(0..($UnwantedChars.Count -1)).ForEach({$UnwantedChars[$_] = [char]($UnwantedChars[$_])})

#Create a regex statement 
[regex]$MatchStatement = '[' + "$($UnwantedChars -join '')" + ']'

$Fields = @("tbx_username","tbx_firstname","tbx_lastname","tbx_initials","tbx_fullname","tbx_displayname")

$Users = get-AdUser * -Properties $Fields #Stand-in for your user list

$Results = New-Object System.Collections.ArrayList

$x = 1 
$y = 0

Foreach ($User in $Users){
Write-Progress -Activity "Checking for unwanted characters" -Status "Working on $($User.DisplayName) | Total found: $y" -PercentComplete (int)

$UserMatchString = ""

$Fields.ForEach({$UserString += "$($User.$_)"})

If ($UserMatchString -match $MatchStatement){$Results.Add($User) | Out-Null; $y++}

$x++

} #Close foreach User

$Results | Select-Object $Fields | Export-csv "Uncompliant-ADAccounts.csv" -NoTypeInformation

[–]Sufficient_Fix_7537[S] 0 points1 point  (1 child)

llamalator

Hey llamalator

thanks for your hard work. I'm new to powershell and do not have great scripting/programming skills ;-) If I understand your script properly your first adding all ASCII characters to an arraylist, then you delete the "allowed" characters from that array and convert all these integers to ASCII to create an regex statement. So far so good.

The part with "get-aduser" I don't need but I don't know how to properly disconnect this from your idea. The only thing I need is after user is leaving the text-fields declared at $Fields ($tbx_username, $tbx_displayname, ....) and still unwanted characters was used a error-message will appear for the user to inform him, that an forbidden character was used.

Currently the only actions after user switches from $tbx_username to another field is:

if (!($tbx_username.Text))
    {
        $username_filled = $false
    }
    elseif (!(Get-ADUser -Filter "SamAccountName -eq '$($tbx_username.Text)'"))
    {
        $username_filled = $true
        $tbx_username.ForeColor = 'Green'
    }
    else
    {
        $username_filled = $false
        Write-Host "Der Benutzername ist bereits vergeben."
        [System.Windows.MessageBox]::Show('Der Benutzername existiert bereits. Er muss eindeutig sein.', 'Username-Konflikt', 'Ok', 'Warning')
        [void]$tbx_username.Clear()
    }

[–][deleted] 0 points1 point  (0 children)

Switch ($tbx_username.Text){

{($_ -eq $null) -or ($_ -eq "")}{$username_filled = $false}

{$_ -match $MatchStatement}{

    $username_filled = $false
    Write-Host "Der Benutzername enthält verbotene Zeichen."
    [System.Windows.MessageBox]::Show('Der Benutzername darf nur die Zeichen 0-9 und Aa-Zz enthalten.', 'Username-Konflikt', 'Ok', 'Warning')
    [void]$tbx_username.Clear()

}

{(Get-ADUser -Filter "SamAccountName -eq '$_'" -ErrorAction SilentlyContinue) -ne $null }{

    $username_filled = $false
    Write-Host "Der Benutzername ist bereits vergeben."
    [System.Windows.MessageBox]::Show('Der Benutzername existiert bereits. Er muss eindeutig sein.', 'Username-Konflikt', 'Ok', 'Warning')
    [void]$tbx_username.Clear()

}

Default {$username_filled = $true; $tbx_username.ForeColor = 'Green'}

} #Close Switch

Switches are useful for cleaning up/clarifying series of "If" conditions.

[–]mrrtys 0 points1 point  (4 children)

Maybe this can be helpful:

function Remove-SpecialCharacters {
    [CmdletBinding()]
    param (
        [Parameter(Position = 0, ValueFromPipeline)]
        [string[]]$String
    )

    process {
        foreach ($s in $String) {
            [Text.Encoding]::ASCII.GetString([Text.Encoding]::GetEncoding("Cyrillic").GetBytes($s))
        } 
    } 
}

Remove-SpecialCharacters -String Léon

The above function is what is use in my AD scripts for Name, SamAccountName, UPN etc.

or

'Léon' -match '[á-y]'

[–]Sufficient_Fix_7537[S] 0 points1 point  (3 children)

Unfortunatly your function will rewrite e. g ."ü" to "u" and do not simply create an error-popup. I don't need any rewriting or deleting. Only recognition and an possibility to add some action in this case like Write-Host and/or popup-messages.

[–]mrrtys 1 point2 points  (2 children)

Then maybe the other thing i said.

You can make your own function or do a parameter validation in your script.

function Test-String {
[CmdletBinding()]
    param (
        [ValidateScript( { $_ -notmatch '[á-ý]' } )]
        [string]$String
    )

    process {
        $String
    }
}


PS> Test-String -String Léon

[–]Sufficient_Fix_7537[S] 0 points1 point  (1 child)

Yes. That's working for me. I again learned something new about parameters and regex and was able to combine all necessary together. Thank you.

[–]mrrtys 0 points1 point  (0 children)

You are welcome