# setup-ftp.ps1 # 必須以系統管理員執行 # 使用相對於腳本的設定檔路徑 $configPath = Join-Path $PSScriptRoot "config.json" if (-not (Test-Path $configPath)) { Write-Error "找不到設定檔:$configPath" exit 1 } try { $configContent = Get-Content $configPath -Raw | ConvertFrom-Json } catch { Write-Error "讀取設定檔失敗:$($_.Exception.Message)" exit 1 } # 取得設定值與預設值處理 $ftpUser = $configContent.ftpUser ?: "ftpuser" $ftpPassword = $configContent.ftpPassword ?: "P@ssw0rd123" $ftpRoot = $configContent.ftpRoot ?: "D:\" $ftpPort = $configContent.ftpPort ?: 21 $ftpSiteName = $env:COMPUTERNAME Write-Host "開始安裝 IIS 與 FTP Server..." # 啟用必要功能 $features = @( "IIS-WebServerRole", "IIS-FTPServer", "IIS-FTPExtensibility", "IIS-ManagementConsole" ) foreach ($feature in $features) { Write-Host "啟用 Windows 功能:$feature" Enable-WindowsOptionalFeature -Online -FeatureName $feature -All -NoRestart -ErrorAction SilentlyContinue } # 重啟 IIS Write-Host "重啟 IIS..." iisreset # 建立 FTP 根目錄 if (-not (Test-Path $ftpRoot)) { Write-Host "建立 FTP 根目錄:$ftpRoot" New-Item -Path $ftpRoot -ItemType Directory | Out-Null } else { Write-Host "FTP 根目錄已存在:$ftpRoot" } # 建立本機使用者 if (-not (Get-LocalUser -Name $ftpUser -ErrorAction SilentlyContinue)) { Write-Host "建立 FTP 使用者帳號:$ftpUser" $securePass = ConvertTo-SecureString $ftpPassword -AsPlainText -Force New-LocalUser -Name $ftpUser -Password $securePass -FullName "FTP User" -Description "FTP專用帳號" -PasswordNeverExpires } else { Write-Host "FTP 使用者帳號已存在:$ftpUser" } # 加入 Users 群組 Add-LocalGroupMember -Group "Users" -Member $ftpUser -ErrorAction SilentlyContinue # 設定權限 $acl = Get-Acl $ftpRoot $rule = New-Object System.Security.AccessControl.FileSystemAccessRule("$env:COMPUTERNAME\$ftpUser", "FullControl", "ContainerInherit,ObjectInherit", "None", "Allow") $acl.AddAccessRule($rule) Set-Acl $ftpRoot $acl Write-Host "設定使用者對 FTP 根目錄的權限完成" # 匯入 WebAdministration 模組 Import-Module WebAdministration # 建立 FTP Site $bindingInformation = "*:$ftpPort:" if (Get-Website -Name $ftpSiteName -ErrorAction SilentlyContinue) { Write-Host "已有同名 FTP Site,刪除:$ftpSiteName" Remove-Website -Name $ftpSiteName } Write-Host "建立 FTP Site:$ftpSiteName" New-Item "IIS:\Sites\$ftpSiteName" -bindings @{protocol="ftp";bindingInformation=$bindingInformation} -physicalPath $ftpRoot # 設定驗證方式 Set-ItemProperty "IIS:\Sites\$ftpSiteName" -Name ftpServer.security.authentication.anonymousAuthentication.enabled -Value $false Set-ItemProperty "IIS:\Sites\$ftpSiteName" -Name ftpServer.security.authentication.basicAuthentication.enabled -Value $true # 授權使用者 Remove-WebConfiguration -Filter "system.ftpServer/security/authorization/authorizationRules" -PSPath "IIS:\Sites\$ftpSiteName" -ErrorAction SilentlyContinue Add-WebConfiguration -PSPath "IIS:\Sites\$ftpSiteName" -Filter "system.ftpServer/security/authorization/authorizationRules" -Value @{ accessType = "Allow" users = $ftpUser permissions = "Read, Write" } # 設定被動模式端口範圍 Set-ItemProperty "IIS:\Sites\$ftpSiteName" -Name ftpServer.firewallSupport.passivePortRange -Value "50000-51000" # 開防火牆例外 if (-not (Get-NetFirewallRule -DisplayName "FTP Server ($ftpPort)" -ErrorAction SilentlyContinue)) { New-NetFirewallRule -DisplayName "FTP Server ($ftpPort)" -Direction Inbound -Protocol TCP -LocalPort $ftpPort -Action Allow -Profile Any } if (-not (Get-NetFirewallRule -DisplayName "FTP Passive Ports" -ErrorAction SilentlyContinue)) { New-NetFirewallRule -DisplayName "FTP Passive Ports" -Direction Inbound -Protocol TCP -LocalPort 50000-51000 -Action Allow -Profile Any } # 啟動 FTP 服務 Start-Service ftpsvc -ErrorAction SilentlyContinue Write-Host "✅ IIS FTP 服務安裝與設定完成!" Write-Host "帳號:" $ftpUser Write-Host "密碼:" $ftpPassword Write-Host "目錄:" $ftpRoot Write-Host "站名:" $ftpSiteName Write-Host "連接埠:" $ftpPort