👥

Active Directory:CSV読み込んでユーザーの新規作成

に公開

オンプレAD環境でCSVを読み込んでアカウントを作成するPowerShellを書いてみた。

前提条件

  • ドメインコントローラーにコンソールかリモートデスクトップでログオンして操作する
  • 管理者の PC から操作する場合は、Active Directory モジュールが使えること
  • 移動対象OU配下内に同一名のOUが存在しないこと

スクリプトの内容

  1. アカウント情報が記載されたCSVの読み込み
  2. ユーザーの存在チェック
  3. OU、所属グループの事前解決
  4. ユーザー作成処理
  5. 所属グループ追加

読み込むCSVのレイアウト

文字コードは、Shift_JIS

ADUserList.csv
"Name","DisplayName","Surname","Givenname","OU","Group","Password"
"test-user01","テストユーザー01","テスト","ユーザー01","testOU01","sec-test01","1234567890hoge+"

レイアウトの説明

項目 説明
Name アカウント名
DisplayName 表示名
Surname
Givenname
OU 所属OU
Group 所属グループ
Password 初期パスワード

完成したスクリプト

New_ADUser.ps1
<#
.SYNOPSIS
    CSV情報から個別のパスワードを用いてADユーザーを安全かつ確実に一括作成する。
#>
Import-Module ActiveDirectory

$CSVFile  = "./ADUserList.csv"
$SearchOU = "OU=〇〇,DC=〇〇,DC=〇〇"
$DOMAIN   = "test.com"

# CSV読み込み
$csvData = Import-Csv $CSVFile -Encoding Default

foreach ($row in $csvData) {
    # データのマッピング
    $TargetUser  = $row.Name
    $DisplayName = $row.DisplayName
    $TargetOU    = $row.OU
    $TargetGroup = $row.Group
    $RawPassword = $row.Password

    try {
        # 1. ユーザーの存在確認(厳格なチェック)
        $null = Get-ADUser -Identity $TargetUser -ErrorAction Stop
        Write-Host "[スキップ] $($TargetUser) は既に存在します。" -ForegroundColor DarkGray
        continue 

    } catch [Microsoft.ActiveDirectory.Management.ADIdentityNotFoundException] {
        # ==========================================
        # 新規作成ルート
        # ==========================================
        try {
            Write-Host "処理中: $($TargetUser) ..." -NoNewline

            # 2. OUの事前解決
            if ([string]::IsNullOrWhiteSpace($TargetOU)) { throw "OUが指定されていません。" }
            $ouSearch = Get-ADOrganizationalUnit -Filter "Name -eq '$TargetOU'" -SearchBase $SearchOU -SearchScope Subtree
            if ($null -eq $ouSearch -or $ouSearch.Count -eq 0) { throw "所属OU '$TargetOU' が見つかりません。" }
            if ($ouSearch.Count -gt 1) { throw "同名OU '$TargetOU' が複数存在し、一意に特定できません。" }

            # 3. グループの事前解決
            $groupObj = $null
            if (-not [string]::IsNullOrWhiteSpace($TargetGroup)) {
                $groupSearch = Get-ADGroup -Filter "Name -eq '$TargetGroup'" -SearchBase $SearchOU -SearchScope Subtree
                if ($null -eq $groupSearch -or $groupSearch.Count -eq 0) { throw "追加グループ '$TargetGroup' が見つかりません。" }
                if ($groupSearch.Count -gt 1) { throw "同名グループ '$TargetGroup' が複数存在します。" }
                $groupObj = $groupSearch
            }

            # 4. パスワードの暗号化処理(ループ内でユーザーごとに都度変換)
            if ([string]::IsNullOrWhiteSpace($RawPassword)) { throw "パスワードがCSVに記載されていません。" }
            $securePassword = ConvertTo-SecureString -AsPlainText $RawPassword -Force

            # 5. ユーザー作成処理
            # -PassThru で作成直後のオブジェクトを掴み、グループ追加のタイミングバグを防ぐ
            $newUser = New-ADUser -Path $ouSearch.DistinguishedName `
                                  -Name $TargetUser `
                                  -DisplayName $DisplayName `
                                  -sAMAccountName $TargetUser `
                                  -Surname $row.Surname `
                                  -Givenname $row.Givenname `
                                  -UserPrincipalName "${TargetUser}@${DOMAIN}" `
                                  -AccountPassword $securePassword `
                                  -ChangePasswordAtLogon $false `
                                  -Enabled $true `
                                  -PasswordNeverExpires $false `
                                  -PassThru `
                                  -ErrorAction Stop

            # 6. グループ追加処理
            if ($null -ne $groupObj) {
                Add-ADGroupMember -Identity $groupObj -Members $newUser -ErrorAction Stop
                Write-Host " [完了] (OU配置 & グループ追加済)" -ForegroundColor Green
            } else {
                Write-Host " [完了] (OU配置のみ)" -ForegroundColor Green
            }

        } catch {
            # 作成フェーズでの各種エラー(OU無し、パスワードポリシー違反など)
            Write-Host " [失敗]" -ForegroundColor Red
            Write-Error "  └ 詳細: $($_.Exception.Message)"
        }
    } catch {
        # 存在確認時の予期せぬ通信エラー等
        Write-Error "[致命的エラー] $($TargetUser) の状態確認中に異常発生: $($_.Exception.Message)"
    }
}

Discussion