Zuletzt aktiv 1789543730

Änderung e22247ac89aba043a547d318151378c63b8d6561

dhcp-scope-monitor.ps1 Orginalformat
1#requires -Version 7.0
2<#
3.SYNOPSIS
4 Universal DHCP Scope Monitoring Utility
5
6.DESCRIPTION
7 Cross-platform DHCP monitoring utility for:
8 - Windows
9 - macOS
10 - Linux (including Debian)
11
12 Execution modes:
13 1. LOCAL : On Windows with the DhcpServer module available.
14 2. REMOTE : On Windows/macOS/Linux using PowerShell Remoting over SSH
15 to a Windows DHCP Server.
16
17 Remote DHCP objects are flattened on the Windows server before being
18 returned to non-Windows clients, avoiding CIM/MI serialization issues
19 such as libmi errors on macOS/Linux.
20
21.EXAMPLE
22 pwsh ./dhcp-monitor-universal.ps1
23
24 On macOS/Linux (or Windows without the local DhcpServer module), the
25 script asks for the DHCP Server hostname/IP and SSH username.
26
27.EXAMPLE
28 pwsh ./dhcp-monitor-universal.ps1 -DhcpServer 192.168.1.10 -UserName "CONTOSO\\administrator"
29
30 Skips the interactive server/username questions.
31
32.EXAMPLE
33 pwsh ./dhcp-monitor-universal.ps1 -Mode Local
34
35 Forces Local mode. Requires Windows and the DhcpServer module.
36
37.NOTES
38 In Remote mode, the script interactively asks for:
39 - DHCP Server hostname or IP address
40 - SSH username
41#>
42
43param (
44 [string]$DhcpServer,
45 [string]$UserName,
46 [ValidateSet("Auto", "Local", "Remote")]
47 [string]$Mode = "Auto"
48)
49
50$ErrorActionPreference = "Stop"
51$script:DhcpSession = $null
52$script:ExecutionMode = $null
53$script:DhcpServer = $DhcpServer
54$script:UserName = $UserName
55
56# ============================================================
57# UI HELPERS
58# ============================================================
59
60function Show-Title {
61 Clear-Host
62 Write-Host "===================================================" -ForegroundColor Cyan
63 Write-Host " Universal DHCP Scope Monitoring Utility" -ForegroundColor Cyan
64 Write-Host "===================================================" -ForegroundColor Cyan
65 Write-Host
66 Write-Host "Client OS : $([System.Runtime.InteropServices.RuntimeInformation]::OSDescription)"
67 Write-Host "Mode : $script:ExecutionMode"
68 if ($script:ExecutionMode -eq "Remote") {
69 Write-Host "DHCP Server : $script:DhcpServer"
70 Write-Host "SSH User : $script:UserName"
71 }
72 Write-Host
73}
74
75function Wait-Enter {
76 param([string]$Message = "Tekan ENTER untuk melanjutkan")
77 [void](Read-Host $Message)
78}
79
80function Convert-ToDisplayString {
81 param($Value)
82 if ($null -eq $Value) { return "" }
83 return $Value.ToString()
84}
85
86# ============================================================
87# CONNECTION / EXECUTION MODE
88# ============================================================
89
90function Test-LocalDhcpModule {
91 if (-not $IsWindows) {
92 return $false
93 }
94
95 return [bool](Get-Module -ListAvailable -Name DhcpServer)
96}
97
98function Connect-DhcpBackend {
99 if ($Mode -eq "Local") {
100 if (-not (Test-LocalDhcpModule)) {
101 throw "Mode Local dipilih, tetapi module DhcpServer tidak tersedia."
102 }
103
104 Import-Module DhcpServer -ErrorAction Stop
105 $script:ExecutionMode = "Local"
106 return
107 }
108
109 if ($Mode -eq "Auto" -and (Test-LocalDhcpModule)) {
110 Import-Module DhcpServer -ErrorAction Stop
111 $script:ExecutionMode = "Local"
112 return
113 }
114
115 $script:ExecutionMode = "Remote"
116
117 Write-Host
118 Write-Host "Remote DHCP Server Configuration" -ForegroundColor Cyan
119 Write-Host "---------------------------------------------------"
120
121 while ([string]::IsNullOrWhiteSpace($script:DhcpServer)) {
122 $script:DhcpServer = Read-Host "DHCP Server hostname / IP"
123 if ([string]::IsNullOrWhiteSpace($script:DhcpServer)) {
124 Write-Host "DHCP Server tidak boleh kosong." -ForegroundColor Red
125 }
126 }
127
128 while ([string]::IsNullOrWhiteSpace($script:UserName)) {
129 $script:UserName = Read-Host "SSH username (contoh: DOMAIN\administrator)"
130 if ([string]::IsNullOrWhiteSpace($script:UserName)) {
131 Write-Host "Username tidak boleh kosong." -ForegroundColor Red
132 }
133 }
134
135 Write-Host
136 Write-Host "Menghubungkan ke Windows DHCP Server..." -ForegroundColor Cyan
137 Write-Host "Server : $script:DhcpServer"
138 Write-Host "User : $script:UserName"
139 Write-Host
140
141 try {
142 $script:DhcpSession = New-PSSession `
143 -HostName $script:DhcpServer `
144 -UserName $script:UserName `
145 -ErrorAction Stop
146
147 Write-Host "Koneksi berhasil." -ForegroundColor Green
148 Start-Sleep -Milliseconds 700
149 }
150 catch {
151 throw "Gagal membuat PowerShell SSH session ke $script:DhcpServer. $($_.Exception.Message)"
152 }
153}
154
155function Disconnect-DhcpBackend {
156 if ($null -ne $script:DhcpSession) {
157 try {
158 Remove-PSSession -Session $script:DhcpSession -ErrorAction SilentlyContinue
159 }
160 catch {}
161 $script:DhcpSession = $null
162 }
163}
164
165function Test-DhcpSession {
166 if ($script:ExecutionMode -ne "Remote") {
167 return $true
168 }
169
170 if ($null -eq $script:DhcpSession) {
171 return $false
172 }
173
174 return ($script:DhcpSession.State -eq "Opened")
175}
176
177# ============================================================
178# DATA ACCESS LAYER
179# ============================================================
180
181function Get-DhcpScopeData {
182 param (
183 [Parameter(Mandatory)]
184 [string]$ScopeId
185 )
186
187 if ($script:ExecutionMode -eq "Local") {
188 $s = Get-DhcpServerv4Scope -ScopeId $ScopeId -ErrorAction Stop
189
190 return [PSCustomObject]@{
191 ScopeId = Convert-ToDisplayString $s.ScopeId
192 Name = $s.Name
193 State = Convert-ToDisplayString $s.State
194 StartRange = Convert-ToDisplayString $s.StartRange
195 EndRange = Convert-ToDisplayString $s.EndRange
196 SubnetMask = Convert-ToDisplayString $s.SubnetMask
197 LeaseDuration = Convert-ToDisplayString $s.LeaseDuration
198 }
199 }
200
201 return Invoke-Command -Session $script:DhcpSession -ArgumentList $ScopeId -ScriptBlock {
202 param($RemoteScopeId)
203
204 $s = Get-DhcpServerv4Scope -ScopeId $RemoteScopeId -ErrorAction Stop
205
206 [PSCustomObject]@{
207 ScopeId = if ($null -eq $s.ScopeId) { "" } else { $s.ScopeId.ToString() }
208 Name = $s.Name
209 State = if ($null -eq $s.State) { "" } else { $s.State.ToString() }
210 StartRange = if ($null -eq $s.StartRange) { "" } else { $s.StartRange.ToString() }
211 EndRange = if ($null -eq $s.EndRange) { "" } else { $s.EndRange.ToString() }
212 SubnetMask = if ($null -eq $s.SubnetMask) { "" } else { $s.SubnetMask.ToString() }
213 LeaseDuration = if ($null -eq $s.LeaseDuration) { "" } else { $s.LeaseDuration.ToString() }
214 }
215 } -ErrorAction Stop
216}
217
218function Get-DhcpStatisticsData {
219 param (
220 [Parameter(Mandatory)]
221 [string]$ScopeId
222 )
223
224 if ($script:ExecutionMode -eq "Local") {
225 $s = Get-DhcpServerv4ScopeStatistics -ScopeId $ScopeId -ErrorAction Stop
226
227 return [PSCustomObject]@{
228 Free = [long]$s.Free
229 InUse = [long]$s.InUse
230 PercentageInUse = [double]$s.PercentageInUse
231 Reserved = [long]$s.Reserved
232 Pending = [long]$s.Pending
233 SuperscopeName = Convert-ToDisplayString $s.SuperscopeName
234 }
235 }
236
237 return Invoke-Command -Session $script:DhcpSession -ArgumentList $ScopeId -ScriptBlock {
238 param($RemoteScopeId)
239
240 $s = Get-DhcpServerv4ScopeStatistics -ScopeId $RemoteScopeId -ErrorAction Stop
241
242 [PSCustomObject]@{
243 Free = [long]$s.Free
244 InUse = [long]$s.InUse
245 PercentageInUse = [double]$s.PercentageInUse
246 Reserved = [long]$s.Reserved
247 Pending = [long]$s.Pending
248 SuperscopeName = if ($null -eq $s.SuperscopeName) { "" } else { $s.SuperscopeName.ToString() }
249 }
250 } -ErrorAction Stop
251}
252
253function Get-DhcpLeaseData {
254 param (
255 [Parameter(Mandatory)]
256 [string]$ScopeId
257 )
258
259 if ($script:ExecutionMode -eq "Local") {
260 $raw = @(Get-DhcpServerv4Lease -ScopeId $ScopeId -ErrorAction Stop)
261
262 return @(
263 foreach ($lease in $raw) {
264 [PSCustomObject]@{
265 IPAddress = Convert-ToDisplayString $lease.IPAddress
266 HostName = Convert-ToDisplayString $lease.HostName
267 ClientId = Convert-ToDisplayString $lease.ClientId
268 AddressState = Convert-ToDisplayString $lease.AddressState
269 LeaseExpiryTime = $lease.LeaseExpiryTime
270 }
271 }
272 )
273 }
274
275 # IMPORTANT:
276 # Materialize the DHCP CIM result first, then flatten every property
277 # while still executing on Windows. This prevents libmi/CIM objects
278 # from crossing the SSH remoting boundary.
279 return @(
280 Invoke-Command -Session $script:DhcpSession -ArgumentList $ScopeId -ScriptBlock {
281 param($RemoteScopeId)
282
283 $rawLeases = @(Get-DhcpServerv4Lease -ScopeId $RemoteScopeId -ErrorAction Stop)
284
285 foreach ($lease in $rawLeases) {
286 $expiry = $null
287
288 if ($null -ne $lease.LeaseExpiryTime) {
289 try {
290 $expiry = $lease.LeaseExpiryTime.ToString("o")
291 }
292 catch {
293 $expiry = $lease.LeaseExpiryTime.ToString()
294 }
295 }
296
297 [PSCustomObject]@{
298 IPAddress = if ($null -eq $lease.IPAddress) { "" } else { $lease.IPAddress.ToString() }
299 HostName = if ($null -eq $lease.HostName) { "" } else { $lease.HostName.ToString() }
300 ClientId = if ($null -eq $lease.ClientId) { "" } else { $lease.ClientId.ToString() }
301 AddressState = if ($null -eq $lease.AddressState) { "" } else { $lease.AddressState.ToString() }
302 LeaseExpiryTime = $expiry
303 }
304 }
305 } -ErrorAction Stop
306 )
307}
308
309# ============================================================
310# NORMALIZATION / SORTING
311# ============================================================
312
313function Convert-LeaseExpiry {
314 param($Value)
315
316 if ($null -eq $Value -or [string]::IsNullOrWhiteSpace($Value.ToString())) {
317 return $null
318 }
319
320 if ($Value -is [datetime]) {
321 return $Value
322 }
323
324 $parsed = [datetime]::MinValue
325
326 if ([datetime]::TryParse(
327 $Value.ToString(),
328 [System.Globalization.CultureInfo]::InvariantCulture,
329 [System.Globalization.DateTimeStyles]::RoundtripKind,
330 [ref]$parsed
331 )) {
332 return $parsed
333 }
334
335 if ([datetime]::TryParse($Value.ToString(), [ref]$parsed)) {
336 return $parsed
337 }
338
339 return $null
340}
341
342function Get-IPv4SortKey {
343 param([string]$IPAddress)
344
345 try {
346 $bytes = [System.Net.IPAddress]::Parse($IPAddress).GetAddressBytes()
347 if ($bytes.Count -ne 4) {
348 return [uint64]::MaxValue
349 }
350
351 return (
352 ([uint64]$bytes[0] -shl 24) -bor
353 ([uint64]$bytes[1] -shl 16) -bor
354 ([uint64]$bytes[2] -shl 8) -bor
355 ([uint64]$bytes[3])
356 )
357 }
358 catch {
359 return [uint64]::MaxValue
360 }
361}
362
363# ============================================================
364# SCOPE FUNCTIONS
365# ============================================================
366
367function Test-DhcpScope {
368 param (
369 [Parameter(Mandatory)]
370 [string]$ScopeId
371 )
372
373 try {
374 [void](Get-DhcpScopeData -ScopeId $ScopeId)
375 return $true
376 }
377 catch {
378 return $false
379 }
380}
381
382function Show-ScopeSummary {
383 param (
384 [Parameter(Mandatory)]
385 [string]$ScopeId
386 )
387
388 try {
389 $scope = Get-DhcpScopeData -ScopeId $ScopeId
390 $stats = Get-DhcpStatisticsData -ScopeId $ScopeId
391
392 Write-Host
393 Write-Host "Summary Scope" -ForegroundColor Yellow
394 Write-Host "---------------------------------------------------"
395
396 [PSCustomObject]@{
397 ScopeId = $scope.ScopeId
398 Name = $scope.Name
399 State = $scope.State
400 StartRange = $scope.StartRange
401 EndRange = $scope.EndRange
402 SubnetMask = $scope.SubnetMask
403 LeaseDuration = $scope.LeaseDuration
404 Free = $stats.Free
405 InUse = $stats.InUse
406 PercentageInUse = ("{0:N2}%" -f [double]$stats.PercentageInUse)
407 Reserved = $stats.Reserved
408 Pending = $stats.Pending
409 SuperscopeName = $stats.SuperscopeName
410 } | Format-List | Out-Host
411
412 Write-Host "---------------------------------------------------"
413
414 if ([double]$stats.PercentageInUse -ge 95) {
415 Write-Host "WARNING: Scope hampir penuh!" -ForegroundColor Red
416 }
417 elseif ([double]$stats.PercentageInUse -ge 80) {
418 Write-Host "WARNING: Pemakaian scope sudah tinggi." -ForegroundColor Yellow
419 }
420 else {
421 Write-Host "Status kapasitas scope masih aman." -ForegroundColor Green
422 }
423
424 Write-Host
425 }
426 catch {
427 Write-Host
428 Write-Host "Gagal membaca Scope $ScopeId." -ForegroundColor Red
429 Write-Host $_.Exception.Message -ForegroundColor DarkRed
430 Write-Host
431 }
432}
433
434# ============================================================
435# DEVICE / LEASE LIST
436# ============================================================
437
438function Show-ScopeClients {
439 param (
440 [Parameter(Mandatory)]
441 [string]$ScopeId
442 )
443
444 Clear-Host
445
446 Write-Host "===================================================" -ForegroundColor Cyan
447 Write-Host " DHCP Lease / Device List" -ForegroundColor Cyan
448 Write-Host "===================================================" -ForegroundColor Cyan
449 Write-Host
450 Write-Host "ScopeId : $ScopeId" -ForegroundColor Yellow
451 Write-Host
452
453 try {
454 $leases = @(Get-DhcpLeaseData -ScopeId $ScopeId)
455
456 if ($leases.Count -eq 0) {
457 Write-Host "Tidak ada lease yang dikembalikan untuk scope ini." -ForegroundColor Yellow
458 Write-Host
459 return
460 }
461
462 $normalized = @(
463 foreach ($lease in $leases) {
464 [PSCustomObject]@{
465 IPAddress = $lease.IPAddress
466 HostName = $lease.HostName
467 ClientId = $lease.ClientId
468 AddressState = $lease.AddressState
469 LeaseExpiryTime = Convert-LeaseExpiry $lease.LeaseExpiryTime
470 }
471 }
472 )
473
474 $normalized |
475 Sort-Object @{ Expression = { Get-IPv4SortKey $_.IPAddress } } |
476 Select-Object IPAddress, HostName, ClientId, AddressState, LeaseExpiryTime |
477 Format-Table -AutoSize |
478 Out-Host
479
480 Write-Host
481 Write-Host "---------------------------------------------------"
482 Write-Host "Total lease : $($normalized.Count)" -ForegroundColor Cyan
483
484 $activeCount = @(
485 $normalized | Where-Object { $_.AddressState -match '^Active' }
486 ).Count
487
488 Write-Host "Active lease: $activeCount" -ForegroundColor Green
489 Write-Host "---------------------------------------------------"
490 Write-Host
491 }
492 catch {
493 Write-Host
494 Write-Host "Gagal membaca daftar lease." -ForegroundColor Red
495 Write-Host $_.Exception.Message -ForegroundColor DarkRed
496 Write-Host
497 }
498}
499
500# ============================================================
501# LEASE ANALYSIS
502# ============================================================
503
504function Show-LeaseAnalysis {
505 param (
506 [Parameter(Mandatory)]
507 [string]$ScopeId
508 )
509
510 Clear-Host
511
512 Write-Host "===================================================" -ForegroundColor Cyan
513 Write-Host " DHCP Lease Analysis" -ForegroundColor Cyan
514 Write-Host "===================================================" -ForegroundColor Cyan
515 Write-Host
516 Write-Host "ScopeId : $ScopeId" -ForegroundColor Yellow
517 Write-Host
518
519 try {
520 $now = Get-Date
521 $scope = Get-DhcpScopeData -ScopeId $ScopeId
522 $stats = Get-DhcpStatisticsData -ScopeId $ScopeId
523 $rawLeases = @(Get-DhcpLeaseData -ScopeId $ScopeId)
524
525 $leases = @(
526 foreach ($lease in $rawLeases) {
527 [PSCustomObject]@{
528 IPAddress = $lease.IPAddress
529 HostName = $lease.HostName
530 ClientId = $lease.ClientId
531 AddressState = $lease.AddressState
532 LeaseExpiryTime = Convert-LeaseExpiry $lease.LeaseExpiryTime
533 }
534 }
535 )
536
537 $leasesWithExpiry = @(
538 $leases | Where-Object { $null -ne $_.LeaseExpiryTime }
539 )
540
541 $expired = @(
542 $leasesWithExpiry |
543 Where-Object { $_.LeaseExpiryTime -lt $now }
544 ).Count
545
546 $expireWithin4Hour = @(
547 $leasesWithExpiry |
548 Where-Object {
549 $_.LeaseExpiryTime -ge $now -and
550 $_.LeaseExpiryTime -le $now.AddHours(4)
551 }
552 ).Count
553
554 $beyond4Hour = @(
555 $leasesWithExpiry |
556 Where-Object { $_.LeaseExpiryTime -gt $now.AddHours(4) }
557 ).Count
558
559 Write-Host "Waktu Pemeriksaan : $now"
560 Write-Host "Lease Duration : $($scope.LeaseDuration)"
561 Write-Host
562
563 Write-Host "Pool Statistics" -ForegroundColor Yellow
564 Write-Host "---------------------------------------------------"
565
566 [PSCustomObject]@{
567 Free = $stats.Free
568 InUse = $stats.InUse
569 PercentageInUse = ("{0:N2}%" -f [double]$stats.PercentageInUse)
570 Reserved = $stats.Reserved
571 Pending = $stats.Pending
572 } | Format-List | Out-Host
573
574 Write-Host
575 Write-Host "Lease Expiration Analysis" -ForegroundColor Yellow
576 Write-Host "---------------------------------------------------"
577
578 [PSCustomObject]@{
579 TotalLease = $leases.Count
580 WithExpiry = $leasesWithExpiry.Count
581 Expired = $expired
582 ExpireWithin4Hour = $expireWithin4Hour
583 Beyond4Hour = $beyond4Hour
584 } | Format-Table -AutoSize | Out-Host
585
586 Write-Host
587 Write-Host "Interpretasi" -ForegroundColor Yellow
588 Write-Host "---------------------------------------------------"
589
590 if ([double]$stats.PercentageInUse -ge 95) {
591 Write-Host "Kapasitas scope : KRITIS (>=95%)." -ForegroundColor Red
592 }
593 elseif ([double]$stats.PercentageInUse -ge 80) {
594 Write-Host "Kapasitas scope : TINGGI (>=80%)." -ForegroundColor Yellow
595 }
596 else {
597 Write-Host "Kapasitas scope : AMAN (<80%)." -ForegroundColor Green
598 }
599
600 if ($leasesWithExpiry.Count -gt 0) {
601 if ($beyond4Hour -gt ($leasesWithExpiry.Count / 2)) {
602 Write-Host "Mayoritas lease masih memiliki expiry lebih dari 4 jam." -ForegroundColor Yellow
603 Write-Host "Kemungkinan masih banyak lease lama dari konfigurasi sebelumnya."
604 }
605 else {
606 Write-Host "Mayoritas lease sudah berada dalam window 4 jam." -ForegroundColor Green
607 }
608 }
609 else {
610 Write-Host "Tidak ada data expiry lease yang dapat dianalisis." -ForegroundColor Yellow
611 }
612
613 Write-Host
614 }
615 catch {
616 Write-Host
617 Write-Host "Gagal melakukan Lease Analysis." -ForegroundColor Red
618 Write-Host $_.Exception.Message -ForegroundColor DarkRed
619 Write-Host
620 }
621}
622
623# ============================================================
624# MAIN PROGRAM
625# ============================================================
626
627try {
628 Connect-DhcpBackend
629
630 while ($true) {
631 Show-Title
632
633 if (-not (Test-DhcpSession)) {
634 throw "PowerShell remote session tidak lagi dalam state Opened."
635 }
636
637 Write-Host "Masukkan ScopeId yang ingin diperiksa." -ForegroundColor Green
638 Write-Host "Contoh: 10.110.114.0"
639 Write-Host
640 Write-Host "Ketik 0 untuk keluar."
641 Write-Host
642
643 $ScopeId = Read-Host "ScopeId"
644
645 if ($ScopeId -eq "0") {
646 break
647 }
648
649 if ([string]::IsNullOrWhiteSpace($ScopeId)) {
650 Write-Host
651 Write-Host "ScopeId tidak boleh kosong." -ForegroundColor Red
652 Write-Host
653 Wait-Enter
654 continue
655 }
656
657 if (-not (Test-DhcpScope -ScopeId $ScopeId)) {
658 Write-Host
659 Write-Host "ScopeId '$ScopeId' tidak ditemukan atau tidak dapat dibaca." -ForegroundColor Red
660 Write-Host
661 Wait-Enter "Tekan ENTER untuk mencoba lagi"
662 continue
663 }
664
665 $changeScope = $false
666
667 while (-not $changeScope) {
668 Show-Title
669 Show-ScopeSummary -ScopeId $ScopeId
670
671 Write-Host "Apa yang ingin dilakukan?" -ForegroundColor Green
672 Write-Host
673 Write-Host "[1] Tampilkan daftar lease / perangkat"
674 Write-Host "[2] Lease Analysis"
675 Write-Host "[3] Cek ScopeId lain"
676 Write-Host "[4] Refresh summary scope ini"
677 Write-Host "[0] Keluar"
678 Write-Host
679
680 $choice = Read-Host "Pilihan"
681
682 switch ($choice) {
683 "1" {
684 Show-ScopeClients -ScopeId $ScopeId
685
686 $clientMenu = $true
687 while ($clientMenu) {
688 Write-Host "Apa yang ingin dilakukan selanjutnya?" -ForegroundColor Green
689 Write-Host
690 Write-Host "[1] Kembali ke summary scope ini"
691 Write-Host "[2] Lease Analysis"
692 Write-Host "[3] Cek ScopeId lain"
693 Write-Host "[4] Refresh daftar lease"
694 Write-Host "[0] Keluar"
695 Write-Host
696
697 $subChoice = Read-Host "Pilihan"
698
699 switch ($subChoice) {
700 "1" {
701 $clientMenu = $false
702 }
703 "2" {
704 Show-LeaseAnalysis -ScopeId $ScopeId
705 Write-Host
706 Wait-Enter "Tekan ENTER untuk kembali"
707 $clientMenu = $false
708 }
709 "3" {
710 $clientMenu = $false
711 $changeScope = $true
712 }
713 "4" {
714 Show-ScopeClients -ScopeId $ScopeId
715 }
716 "0" {
717 return
718 }
719 default {
720 Write-Host
721 Write-Host "Pilihan tidak valid." -ForegroundColor Red
722 Write-Host
723 }
724 }
725 }
726 }
727
728 "2" {
729 Show-LeaseAnalysis -ScopeId $ScopeId
730
731 $analysisMenu = $true
732 while ($analysisMenu) {
733 Write-Host "Apa yang ingin dilakukan selanjutnya?" -ForegroundColor Green
734 Write-Host
735 Write-Host "[1] Kembali ke summary scope ini"
736 Write-Host "[2] Tampilkan daftar lease / perangkat"
737 Write-Host "[3] Cek ScopeId lain"
738 Write-Host "[4] Refresh Lease Analysis"
739 Write-Host "[0] Keluar"
740 Write-Host
741
742 $subChoice = Read-Host "Pilihan"
743
744 switch ($subChoice) {
745 "1" {
746 $analysisMenu = $false
747 }
748 "2" {
749 Show-ScopeClients -ScopeId $ScopeId
750 Write-Host
751 Wait-Enter "Tekan ENTER untuk kembali"
752 $analysisMenu = $false
753 }
754 "3" {
755 $analysisMenu = $false
756 $changeScope = $true
757 }
758 "4" {
759 Show-LeaseAnalysis -ScopeId $ScopeId
760 }
761 "0" {
762 return
763 }
764 default {
765 Write-Host
766 Write-Host "Pilihan tidak valid." -ForegroundColor Red
767 Write-Host
768 }
769 }
770 }
771 }
772
773 "3" {
774 $changeScope = $true
775 }
776
777 "4" {
778 # Loop refreshes summary.
779 }
780
781 "0" {
782 return
783 }
784
785 default {
786 Write-Host
787 Write-Host "Pilihan tidak valid." -ForegroundColor Red
788 Start-Sleep -Seconds 1
789 }
790 }
791 }
792 }
793}
794catch {
795 Write-Host
796 Write-Host "FATAL ERROR" -ForegroundColor Red
797 Write-Host "---------------------------------------------------"
798 Write-Host $_.Exception.Message -ForegroundColor Red
799 Write-Host
800 exit 1
801}
802finally {
803 Disconnect-DhcpBackend
804 Write-Host
805 Write-Host "Keluar dari Universal DHCP Scope Monitoring Utility." -ForegroundColor Cyan
806 Write-Host
807}
808