2026-10-20 20:56:22 +09:00
<UserControl xmlns= "http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x= "http://schemas.microsoft.com/winfx/2006/xaml"
Background= "{StaticResource BgDarkBrush}" >
<Grid Margin= "24" >
<Grid.RowDefinitions>
<!-- 0. Header -->
<RowDefinition Height= "Auto" />
<!-- 1. Main 2-Column Split Layout -->
<RowDefinition Height= "*" />
</Grid.RowDefinitions>
<!-- 0. Header -->
<DockPanel Grid.Row= "0" Margin= "0,0,0,18" >
<StackPanel>
<TextBlock Text= "인프라 일괄 작업 센터 (Batch Workstation)" FontSize= "24" FontWeight= "Bold" Foreground= "#FFFFFF" />
<TextBlock Text= "다중 사용자 계정, Share 권한, AD 보안그룹 및 NetApp Quota 변경을 단일 트랜잭션으로 구성하여 시뮬레이션 후 일괄 실행합니다."
FontSize= "13" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,4,0,0" />
</StackPanel>
<StackPanel Orientation= "Horizontal" HorizontalAlignment= "Right" VerticalAlignment= "Center" >
<Button x:Name= "BtnResetWorkstation" Content= "작업 폼 초기화" Style= "{StaticResource SecondaryButtonStyle}" Margin= "0,0,8,0" Padding= "12,6" />
<Button x:Name= "BtnOpenResolverStandalone" Content= "🔍 동명이인 / 계정 검증기" Style= "{StaticResource PrimaryButtonStyle}" Padding= "12,6" />
</StackPanel>
</DockPanel>
<!-- 1. Main Split Layout -->
<Grid Grid.Row= "1" >
<Grid.ColumnDefinitions>
<!-- Left: Modular Parameter Inputs (운영자가 자유롭게 조합하는 폼) -->
<ColumnDefinition Width= "5*" />
<!-- Right: Simulation (Dry-Run) Preview & Execution Grid -->
<ColumnDefinition Width= "6*" />
</Grid.ColumnDefinitions>
<!-- LEFT: Action Config Form (Scrollable) -->
<ScrollViewer Grid.Column= "0" VerticalScrollBarVisibility= "Auto" Margin= "0,0,12,0" >
<StackPanel>
<!-- Card 1: Target Users Specification -->
<Border Style= "{StaticResource ModernCardStyle}" Margin= "0,0,0,14" >
<StackPanel>
<DockPanel Margin= "0,0,0,10" >
<TextBlock Text= "1. 대상 사용자 지정 (Multi-User Input)" FontSize= "14.5" FontWeight= "Bold" Foreground= "#FFFFFF" />
<Button x:Name= "BtnLaunchResolver" Content= "🔍 동명이인 검증기에서 불러오기..." Style= "{StaticResource PrimaryButtonStyle}" Padding= "10,4" FontSize= "11.5" HorizontalAlignment= "Right" />
</DockPanel>
<TextBlock Text= "사용자 ID 또는 이름 (줄바꿈 / 쉼표로 다중 입력 가능):" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<TextBox x:Name= "TxtWsUserTokens" Height= "70" AcceptsReturn= "True" TextWrapping= "Wrap"
Style= "{StaticResource ModernTextBoxStyle}" Margin= "0,0,0,8"
Text= "gdhong, cskim, yylee" />
<DockPanel>
<TextBlock x:Name= "TxtTargetUsersSummary" Text= "현재 3명의 사용자가 지정되었습니다." FontSize= "11.5" Foreground= "#60A5FA" VerticalAlignment= "Center" />
<Button x:Name= "BtnQuickCheckUsers" Content= "빠른 계정 확인" Style= "{StaticResource SecondaryButtonStyle}" Padding= "8,2" FontSize= "11" HorizontalAlignment= "Right" />
</DockPanel>
</StackPanel>
</Border>
<!-- Card 2: Share & AD Security Group Association -->
<Border Style= "{StaticResource ModernCardStyle}" Margin= "0,0,0,14" >
<StackPanel>
<TextBlock Text= "2. 공유 권한 및 AD 보안그룹 설정" FontSize= "14.5" FontWeight= "Bold" Foreground= "#FFFFFF" Margin= "0,0,0,10" />
<Grid Margin= "0,0,0,8" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width= "*" />
<ColumnDefinition Width= "*" />
</Grid.ColumnDefinitions>
<StackPanel Grid.Column= "0" Margin= "0,0,8,0" >
<TextBlock Text= "대상 Share (공유) 선택 / 입력:" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<ComboBox x:Name= "CmbWsShare" Height= "34" >
<ComboBoxItem Content= "Finance_Share" IsSelected= "True" />
<ComboBoxItem Content= "HR_Share" />
<ComboBoxItem Content= "DevOps_Share" />
<ComboBoxItem Content= "Public_Projects" />
</ComboBox>
</StackPanel>
<StackPanel Grid.Column= "1" Margin= "8,0,0,0" >
<TextBlock Text= "작업 유형 (Action):" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<StackPanel Orientation= "Horizontal" VerticalAlignment= "Center" Margin= "0,6,0,0" >
<RadioButton x:Name= "RadActionAdd" Content= "권한 추가 (Grant)" IsChecked= "True" Foreground= "#FFFFFF" Margin= "0,0,16,0" />
<RadioButton x:Name= "RadActionRemove" Content= "권한 해제 (Revoke)" Foreground= "#FFFFFF" />
</StackPanel>
</StackPanel>
</Grid>
<CheckBox x:Name= "ChkWsSyncAdGroup" Content= "Share 이름과 동일한 AD 보안그룹 멤버십 자동 동기화" IsChecked= "True"
2026-10-20 21:34:57 +09:00
Foreground= "#93C5FD" FontWeight= "SemiBold" Margin= "0,4,0,8" />
<!-- Multi-DC Active Discovery Box -->
<Border Background= "#161F30" BorderBrush= "#2563EB" BorderThickness= "1" CornerRadius= "6" Padding= "10" Margin= "0,4,0,0" >
<StackPanel>
<DockPanel Margin= "0,0,0,4" >
<TextBlock Text= "⚡ 다중 DC (6대) 복제 지연 방지 전략" FontSize= "12" FontWeight= "Bold" Foreground= "#60A5FA" />
<Button x:Name= "BtnDetectActiveDc" Content= "NetApp 활성 DC 감지" Style= "{StaticResource SecondaryButtonStyle}" Padding= "6,2" FontSize= "10.5" HorizontalAlignment= "Right" />
</DockPanel>
<CheckBox x:Name= "ChkDirectActiveDc" Content= "NetApp이 현재 바라보는 활성 DC에 직접 보안그룹 생성 (복제 대기 0초)" IsChecked= "True"
Foreground= "#E2E8F0" FontSize= "11.5" Margin= "0,2,0,4" />
<TextBlock x:Name= "TxtWsActiveDcInfo" Text= "Active DC: [확인 대기] NetApp CIFS 도메인 컨트롤러 바인딩 탐색" FontSize= "11" Foreground= "#38BDF8" Margin= "20,0,0,4" />
<CheckBox x:Name= "ChkBgDcSync" Content= "나머지 5대 DC로 백그라운드 비동기 복제 병행 (Sync-ADObject)" IsChecked= "True"
Foreground= "#94A3B8" FontSize= "11" Margin= "20,0,0,0" />
</StackPanel>
</Border>
2026-10-20 20:56:22 +09:00
</StackPanel>
</Border>
<!-- Card 3: NetApp Qtree & Quota Limit (Optional Module) -->
<Border Style= "{StaticResource ModernCardStyle}" Margin= "0,0,0,14" >
<StackPanel>
<DockPanel Margin= "0,0,0,10" >
<TextBlock Text= "3. NetApp Qtree 및 Quota 용량 조정 (선택 사항)" FontSize= "14.5" FontWeight= "Bold" Foreground= "#FFFFFF" />
<CheckBox x:Name= "ChkWsEnableQuota" Content= "Quota 조정 활성화" IsChecked= "True"
Foreground= "#10B981" FontWeight= "Bold" HorizontalAlignment= "Right" />
</DockPanel>
<Grid Margin= "0,0,0,8" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width= "*" />
<ColumnDefinition Width= "*" />
</Grid.ColumnDefinitions>
<StackPanel Grid.Column= "0" Margin= "0,0,8,0" >
<TextBlock Text= "대상 볼륨 / Qtree:" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<TextBox x:Name= "TxtWsTargetQtree" Text= "/vol/vol_cifs_share01/Finance_Share" Style= "{StaticResource ModernTextBoxStyle}" />
</StackPanel>
<StackPanel Grid.Column= "1" Margin= "8,0,0,0" >
<TextBlock Text= "Quota 적용 단위:" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<ComboBox x:Name= "CmbWsQuotaUnit" SelectedIndex= "0" Height= "34" >
<ComboBoxItem Content= "사용자별 (User Quota)" />
<ComboBoxItem Content= "트리 전체 (Tree Quota)" />
<ComboBoxItem Content= "그룹별 (Group Quota)" />
</ComboBox>
</StackPanel>
</Grid>
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width= "*" />
<ColumnDefinition Width= "*" />
</Grid.ColumnDefinitions>
<StackPanel Grid.Column= "0" Margin= "0,0,8,0" >
<TextBlock Text= "새 Soft Limit (GB):" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<TextBox x:Name= "TxtWsSoftLimit" Text= "450" Style= "{StaticResource ModernTextBoxStyle}" />
</StackPanel>
<StackPanel Grid.Column= "1" Margin= "8,0,0,0" >
<TextBlock Text= "새 Hard Limit (GB):" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<TextBox x:Name= "TxtWsHardLimit" Text= "500" Style= "{StaticResource ModernTextBoxStyle}" />
</StackPanel>
</Grid>
</StackPanel>
</Border>
<!-- Card 4: Audit Reason & Ticket Information -->
<Border Style= "{StaticResource ModernCardStyle}" Margin= "0,0,0,14" >
<StackPanel>
<TextBlock Text= "4. 작업 사유 및 감사/승인 정보 (Audit Information)" FontSize= "14.5" FontWeight= "Bold" Foreground= "#FFFFFF" Margin= "0,0,0,10" />
<TextBlock Text= "처리 사유 (필수 입력):" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<TextBox x:Name= "TxtWsReason" Text= "2026 하반기 신규 프로젝트 투입에 따른 권한 및 Quota 일괄 부여"
Style= "{StaticResource ModernTextBoxStyle}" Margin= "0,0,0,10" />
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width= "*" />
<ColumnDefinition Width= "*" />
</Grid.ColumnDefinitions>
<StackPanel Grid.Column= "0" Margin= "0,0,8,0" >
<TextBlock Text= "ITSM / 결재 티켓 번호:" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<TextBox x:Name= "TxtWsTicketNo" Text= "SR-20261020-088" Style= "{StaticResource ModernTextBoxStyle}" />
</StackPanel>
<StackPanel Grid.Column= "1" Margin= "8,0,0,0" >
<TextBlock Text= "권한 만료일 (임시 권한 시):" FontSize= "12" Foreground= "{StaticResource TextSecondaryBrush}" Margin= "0,0,0,4" />
<TextBox x:Name= "TxtWsExpireDate" Text= "9999-12-31 (무기한)" Style= "{StaticResource ModernTextBoxStyle}" />
</StackPanel>
</Grid>
</StackPanel>
</Border>
</StackPanel>
</ScrollViewer>
<!-- RIGHT: Simulation (Dry-Run) & Execution Console -->
<Border Grid.Column= "1" Style= "{StaticResource ModernCardStyle}" Margin= "12,0,0,0" Padding= "14" >
<Grid>
<Grid.RowDefinitions>
<!-- Simulation Action Bar -->
<RowDefinition Height= "Auto" />
<!-- Simulation Grid Preview -->
<RowDefinition Height= "*" />
<!-- Execution Console Log -->
<RowDefinition Height= "160" />
</Grid.RowDefinitions>
<!-- 1. Simulation Controls -->
<DockPanel Grid.Row= "0" Margin= "0,0,0,12" >
<StackPanel>
<TextBlock Text= "실행 영향도 분석 및 시뮬레이션 (Dry-Run Preview)" FontSize= "14.5" FontWeight= "Bold" Foreground= "#FFFFFF" />
<TextBlock Text= "실제 인프라에 반영하기 전 변경 예정 항목을 안전하게 사전 검증합니다." FontSize= "11.5" Foreground= "{StaticResource TextSecondaryBrush}" />
</StackPanel>
<StackPanel Orientation= "Horizontal" HorizontalAlignment= "Right" >
<Button x:Name= "BtnRunDryRun" Content= "👁 사전 시뮬레이션 (Dry-Run)" Style= "{StaticResource SecondaryButtonStyle}" Margin= "0,0,8,0" Padding= "12,6" />
<Button x:Name= "BtnApplyBatch" Content= "⚡ 최종 일괄 실행 (Apply)" Style= "{StaticResource PrimaryButtonStyle}" Padding= "16,6" FontWeight= "Bold" />
</StackPanel>
</DockPanel>
<!-- 2. Simulation Items DataGrid -->
<DataGrid x:Name= "GridSimulationResults" Grid.Row= "1" Style= "{StaticResource ModernDataGridStyle}" Margin= "0,0,0,12" >
<DataGrid.Columns>
<DataGridTextColumn Header= "순번" Binding= "{Binding StepNo}" Width= "50" />
<DataGridTextColumn Header= "대상 시스템" Binding= "{Binding TargetSystem}" Width= "120" />
<DataGridTextColumn Header= "작업 항목" Binding= "{Binding ActionItem}" Width= "130" />
<DataGridTextColumn Header= "대상 객체 / 사용자" Binding= "{Binding TargetObject}" Width= "150" />
<DataGridTextColumn Header= "변경 전 상태" Binding= "{Binding BeforeState}" Width= "110" />
<DataGridTextColumn Header= "변경 예정 상태" Binding= "{Binding AfterState}" Width= "120" />
<DataGridTextColumn Header= "사전 검증" Binding= "{Binding ValidationResult}" Width= "*" />
</DataGrid.Columns>
</DataGrid>
<!-- 3. Bottom Execution Log Console -->
<Border Grid.Row= "2" Background= "#090D16" CornerRadius= "6" Padding= "10" >
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height= "Auto" />
<RowDefinition Height= "*" />
</Grid.RowDefinitions>
<DockPanel Grid.Row= "0" Margin= "0,0,0,4" >
<TextBlock Text= "일괄 트랜잭션 실행 로그 (Execution Output):" FontSize= "11.5" FontWeight= "SemiBold" Foreground= "#94A3B8" />
<TextBlock x:Name= "TxtWsExecutionStatus" Text= "대기 중 - 시뮬레이션을 실행하십시오." FontSize= "11.5" Foreground= "#60A5FA" HorizontalAlignment= "Right" />
</DockPanel>
<ScrollViewer Grid.Row= "1" VerticalScrollBarVisibility= "Auto" >
<TextBox x:Name= "TxtWsConsoleLog" Background= "Transparent" Foreground= "#A78BFA" BorderThickness= "0"
IsReadOnly= "True" FontFamily= "Consolas" FontSize= "11.5" TextWrapping= "Wrap"
Text= "[준비 완료] 좌측 폼에 필요한 파라미터를 입력하고 [사전 시뮬레이션(Dry-Run)]을 실행하십시오." />
</ScrollViewer>
</Grid>
</Border>
</Grid>
</Border>
</Grid>
</Grid>
</UserControl>