diff --git a/PSWorkItem.psd1 b/PSWorkItem.psd1 index aa65958..5469f44 100644 --- a/PSWorkItem.psd1 +++ b/PSWorkItem.psd1 @@ -4,7 +4,7 @@ @{ RootModule = 'PSWorkItem.psm1' - ModuleVersion = '1.4.0' + ModuleVersion = '1.5.0' CompatiblePSEditions = 'Core' GUID = '4d3ff215-69ea-4fe6-8ad6-97ffc3a15bfb' Author = 'Jeff Hicks' diff --git a/PSWorkItem.psm1 b/PSWorkItem.psm1 index 4684dcc..60dafc4 100644 --- a/PSWorkItem.psm1 +++ b/PSWorkItem.psm1 @@ -3,11 +3,11 @@ # write-host "Importing with culture $(Get-Culture)" if ((Get-Culture).Name -match "\w+") { - Import-LocalizedData -BindingVariable strings -FileName strings.psd1 + Import-LocalizedData -BindingVariable strings } else { #force using En-US if no culture found, which might happen on non-Windows systems. - Import-LocalizedData -BindingVariable strings -FileName strings.psd1 -BaseDirectory .\en-us + Import-LocalizedData -BindingVariable strings -FileName PSWorkItem.psd1 -BaseDirectory .\en-us } if (-Not $ISWindows) { diff --git a/changelog.md b/changelog.md index 35f2a8d..58b8f5b 100644 --- a/changelog.md +++ b/changelog.md @@ -1,6 +1,19 @@ # Changelog for PSWorkItem ## [Unreleased] +### Added +- Added a feature in `Open-PSWorkItemConsole` to allow the user to right-click on a table row and display PSWorkItem details in a pop-up window. +- Added menu choices in Open-PSWorkItemConsole` to manage categories. +- Added additional verbose output. + +### Changed +- Modified private helper functions to support Verbose output. +- Renamed localized string data file to match module name. + +### Fixed +- Fixed typo in strings file +- Fixed `Open-PSWorkItemConsole` to refresh report table when modifiying or removing PSWorkItems. +- Fixed bug in `Remove-PSWorkItemCategory` that wasn't detecting the category value from the dynamic parameter. ## [1.4.0] - 2023-09-29 diff --git a/docs/Add-PSWorkItemCategory.md b/docs/Add-PSWorkItemCategory.md index 70a065c..9bdacad 100644 --- a/docs/Add-PSWorkItemCategory.md +++ b/docs/Add-PSWorkItemCategory.md @@ -20,7 +20,9 @@ Add-PSWorkItemCategory [-Category] [[-Description] ] ## DESCRIPTION -When you setup a new PSWorkItem database, it will define the default categories of Personal, Work, Project, and Other. You may want to add categories. The category must be defined before you can use it. The category will not be added if it already exists unless you use -Force. Or if you need to update a category description you can re-add it with -Force. If the category name needs to be edited, remove the category and re-add it. +When you setup a new PSWorkItem database, it will define the default categories of Personal, Work, Project, and Other. You may want to add categories. The category must be defined before you can use it. The category will not be added if it already exists unless you use -Force. + +It is recommended that you use proper casing for your category names and that they be single words. ## EXAMPLES @@ -160,7 +162,6 @@ This cmdlet supports the common parameters: -Debug, -ErrorAction, -ErrorVariable ## OUTPUTS - ### None ### PSWorkItemCategory diff --git a/docs/Open-PSWorkItemConsole.md b/docs/Open-PSWorkItemConsole.md index 7de4f2e..5db4330 100644 --- a/docs/Open-PSWorkItemConsole.md +++ b/docs/Open-PSWorkItemConsole.md @@ -73,7 +73,7 @@ This cmdlet supports the common parameters: -Debug, -ErrorAction, -ErrorVariable ## NOTES -You cannot specify a completion date using this tool. You must manage categories using the module commands. +You cannot specify a PSWorkItem completion date using this tool. If you have difficulty seeing the cursor in text fields, and you are running in Windows Terminal, you might try changing the cursor in your Windows Terminal profile setting. @@ -88,3 +88,9 @@ IMPORTANT: This command relies on a specific version of Terminal.Gui assembly. Y [Remove-PSWorkItem](Remove-PSWorkItem.md) [Complete-PSWorkItem](Complete-PSWorkItem.md) + +[Add-PSWorkItemCategory](Add-PSWorkItemCategory.md) + +[Set-PSWorkItemCategory](Set-PSWorkItemCategory.md) + +[Remove-PSWorkItemCategory](Remove-PSWorkItemCategory.md) diff --git a/en-us/strings.psd1 b/en-us/PSWorkItem.psd1 similarity index 97% rename from en-us/strings.psd1 rename to en-us/PSWorkItem.psd1 index 50720a3..c5580d3 100644 --- a/en-us/strings.psd1 +++ b/en-us/PSWorkItem.psd1 @@ -47,7 +47,7 @@ InvalidHost = This must be run in a console host. Detected PowerShell host: {0} MoveItem = Moving PSWorkItem to Archive. NoPreferenceFile = No PSWorkItem preference file found at {0}. Run Update-PSWorkItemPreferences to create it." OpenDBConnection = Opening a SQLite database connection -ProcessCategory = Processing {PSWorkItem category {0} +ProcessCategory = Processing PSWorkItem category {0} PSVersion = Running under PowerShell version {0} Refiltering = Re-Filtering found {0} PSWorkItems RefilteringTasks = Re-filtering for PSWorkItems due in the next {0} day(s) @@ -69,6 +69,7 @@ UpdateArchiveTable = Updating archive table value UpdatePreference = Updating PSWorkItem user preferences UpdateTaskTable = Updating tasks table values UsingDB = Using SQLite database {0} +UsingModule = Using module PSWorkItem version {0} ValidateCategory = Validating PSWorkItem category {0} ValidateMove = Validating the move WarnNoTasksFound = Failed to find any matching open PSWorkItems diff --git a/functions/private/tui-helpers.ps1 b/functions/private/tui-helpers.ps1 index 1717079..e3c9ab3 100644 --- a/functions/private/tui-helpers.ps1 +++ b/functions/private/tui-helpers.ps1 @@ -50,8 +50,9 @@ Function ConvertTo-DataTable { Function ClearForm { #clear entry forms but leave category and path + [CmdletBinding()] Param() - + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" $txtTaskName.Text = '' $txtDescription.Text = '' $chkWhatIf.Checked = $False @@ -65,10 +66,13 @@ Function ClearForm { $StatusBar.Items[3].Title = 'Ready' $txtTaskName.SetFocus() [Terminal.Gui.Application]::Refresh() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" } Function ResetForm { + [CmdletBinding()] Param( ) + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" $txtTaskName.Text = '' $txtDescription.Text = '' $chkWhatIf.Checked = $False @@ -87,32 +91,41 @@ Function ResetForm { RefreshCategoryList RefreshTable [Terminal.Gui.Application]::Refresh() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" } Function ShowHelp { + [CmdletBinding()] Param() + + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" + $title = 'Open-PSWorkItemConsole' $help = (Get-Help Open-PSWorkItemConsole).Description.Text | Out-String $dialog = [Terminal.Gui.Dialog]@{ - Title ='Help Open-PSWorkItemConsole' - TextAlignment = "Left" - Width = 75 - Height = 20 - Text = $help + Title = 'Help Open-PSWorkItemConsole' + TextAlignment = 'Left' + Width = 75 + Height = 20 + Text = $help } $ok = [Terminal.Gui.Button]@{ - Text="OK" + Text = 'OK' } - $ok.Add_Clicked({$dialog.RequestStop()}) + $ok.Add_Clicked({ $dialog.RequestStop() }) $dialog.AddButton($ok) - + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Invoking dialog" [Terminal.Gui.Application]::Run($dialog) + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" } + Function RefreshTable { + [CmdletBinding()] Param( [string]$FilterCategory = '*' ) + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" $TableView.RemoveAll() $TableView.Clear() $Data = Get-PSWorkItem -Path $txtPath.Text.ToString() -All | Where-Object { $_.Category -Like $FilterCategory } | @@ -143,18 +156,32 @@ Function RefreshTable { ) $TableView.SetNeedsDisplay() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" } Function RefreshCategoryList { + [CmdletBinding()] Param() - + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" $src = (Get-PSWorkItemCategory -Path $txtPath.Text.ToString()).Category | Sort-Object + $src | Write-Verbose + $dropCategory.Clear() $dropCategory.SetSource($src) + $dropCategory.SetNeedsDisplay() + [Terminal.Gui.Application]::Refresh() + $dropCategory.SelectedItem = 0 #create a lookup list $script:CatList = [System.Collections.Generic.List[string]]::New() $script:CatList.AddRange([string[]]$src) - $lblReport.Text = (Get-PSWorkItemReport -Path $txtPath.Text.ToString() | Format-Table Category, Count, PctTotal | Out-String).Trim() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" +} +Function UpdateReport { + Param() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" + $lblReport.Text = (Get-PSWorkItemReport -Path $txtPath.Text.ToString() | + Format-Table Category, Count, PctTotal | Out-String).Trim() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" } Function ShowWhatIf { @@ -163,11 +190,11 @@ Function ShowWhatIf { [string]$Command, [string]$ID ) - + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" Switch ($command) { 'New' { $cmd = 'New-PSWorkItem' - $cat = $script:CatList[$dropCategory.SelectedItem] + $cat = $dropCategory.Source.ToList()[$dropCategory.SelectedItem] if ($txtDays.Enabled) { #calculate Date $due = (Get-Date).AddDays( $txtDays.Text.ToString()) @@ -186,7 +213,7 @@ Using database: {2} } 'Set' { $cmd = 'Set-PSWorkItem' - $cat = $script:CatList[$dropCategory.SelectedItem] + $cat = $dropCategory.Source.ToList()[$dropCategory.SelectedItem] if ($txtDays.Enabled) { #calculate Date $due = (Get-Date).AddDays( $txtDays.Text.ToString()) @@ -225,13 +252,15 @@ Using database: {2} } } #switch + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Show message box" [Terminal.Gui.MessageBox]::Query('WhatIf Operation', $msg, @('Ok')) - + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" } Function OpenDatabase { + [CmdletBinding()] Param() - + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" $Dialog = [Terminal.Gui.OpenDialog]::new('Open PSWorkItem Database', '') $Dialog.CanChooseDirectories = $false $Dialog.CanChooseFiles = $true @@ -245,9 +274,13 @@ Function OpenDatabase { RefreshCategoryList RefreshTable } + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" } + Function ShowAbout { + [CmdletBinding()] Param() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" $TerminalGuiVersion = [System.Reflection.Assembly]::GetAssembly([Terminal.Gui.Application]).GetName().version $NStackVersion = [System.Reflection.Assembly]::GetAssembly([NStack.UString]).GetName().version $SQLiteVersion = [System.Reflection.Assembly]::GetAssembly([System.Data.Sqlite.SqLiteConnection]).GetName().version @@ -260,22 +293,28 @@ Terminal.Gui $TerminalGuiVersion NStack $NStackVersion System.Data.SQLite $SQLiteVersion "@ - -[Terminal.Gui.MessageBox]::Query('About Open-PSWorkItemConsole', $About, @('Ok')) - +Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Show message box" + [Terminal.Gui.MessageBox]::Query('About Open-PSWorkItemConsole', $About, @('Ok')) + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" } Function UpdateStatusTime { + [CmdletBinding()] Param() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" $StatusBar.Items[0].Title = Get-Date -Format g + [Terminal.Gui.Application]::Refresh() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" #need to return a Boolean result Return $True } Function Populate { + [CmdletBinding()] Param() - <# sample + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" + <# sample $TableView.table.rows[$TableView.SelectedRow] ID : 21 @@ -285,25 +324,482 @@ Function Populate { Progress : 0 Category : Blog #> - $item = $TableView.table.rows[$TableView.SelectedRow] - if ($item.Overdue) { - $lblOverDue.Visible = $True + $item = $TableView.table.rows[$TableView.SelectedRow] + if ($item.Overdue) { + $lblOverDue.Visible = $True + } + else { + $lblOverDue.Visible = $False + } + If ($item.Description -match '\w+') { + $chkClearDescription.Visible = $True + } + else { + $chkClearDescription.Visible = $False + } + $txtTaskName.Text = $item.Name + $txtDueDate.Text = '{0:g}' -f $item.DueDate + $radioGrp.SelectedItem = 1 + $txtDays.Enabled = $False + $txtDescription.Text = $item.Description + $dropCategory.SelectedItem = $script:CatList.FindIndex({ $args -eq $item.Category }) + $txtProgress.Text = $item.Progress + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" +} + +Function AddCategory { + [CmdletBinding()] + Param() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" + $cs = [Terminal.Gui.ColorScheme]::New() + $cs.Normal = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::Black, [Terminal.Gui.Color]::Gray) + $cs.Focus = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::White, [Terminal.Gui.Color]::DarkGray) + $cs.HotNormal = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::BrightBlue, [Terminal.Gui.Color]::Gray) + $subWin = [Terminal.Gui.Dialog]@{ + Title = 'Add Category' + X = [Terminal.Gui.Pos]::Center() + Y = [Terminal.Gui.Pos]::Center() + Width = 50 + Height = 10 + ColorScheme = $cs + } + + $lblCategory = [Terminal.Gui.Label]@{ + X = 1 + Y = 1 + Width = 10 + Height = 1 + Text = 'New Category' + TabStop = $False + } + + $txtCategory = [Terminal.Gui.TextField]@{ + X = $lblCategory.Frame.Width + 3 + Y = 1 + Width = 30 + Height = 1 + } + $lblDescription = [Terminal.Gui.Label]@{ + X = 1 + Y = 3 + Width = 10 + Height = 1 + Text = 'Description' + TabStop = $False + } + $txtDescription = [Terminal.Gui.TextField]@{ + X = $txtCategory.X + Y = 3 + Width = 30 + Height = 1 + } + + $chkWhatIf = [Terminal.Gui.CheckBox]@{ + X = 1 + Y = 5 + Width = 10 + Height = 1 + Text = 'WhatIf' + } + $chkForce = [Terminal.Gui.CheckBox]@{ + X = 1 + Y = 6 + Width = 10 + Height = 1 + Text = 'Force' + } + $btnOk = [Terminal.Gui.Button]@{ + X = 13 + Y = 6 + Width = 10 + Height = 1 + Text = 'Ok' + } + $btnOK.Add_Clicked({ + if ($txtCategory.Text.ToString() -match '\w+') { + if ($chkWhatIf.Checked) { + $msg = @" + +Category = $($txtCategory.Text.ToString()) +Description = $($txtDescription.Text.ToString()) +Force = $($chkForce.Checked) +Path = $($txtPath.Text.ToString()) +"@ + [Terminal.Gui.MessageBox]::Query('Add-PSWorkitemCategory -WhatIf', $msg, @('Ok')) + } + else { + $splat = @{ + Category = $txtCategory.Text.ToString() + Path = $txtPath.Text.ToString() + ErrorAction = 'Stop' + WarningVariable = 'warn' + } + if ($chkForce.Checked) { + $splat['Force'] = $True + } + if ($txtDescription.Text.ToString() -match '\w+') { + $splat['Description'] = $txtDescription.Text.ToString() + } + Try { + Add-PSWorkItemCategory @splat + if ($warn) { + [Terminal.Gui.MessageBox]::ErrorQuery('Warning', $warn.message) + } + else { + RefreshCategoryList + UpdateStatusTime + $subWin.RequestStop() + } + } + Catch { + [Terminal.Gui.MessageBox]::ErrorQuery('Error', $_.Exception.Message) + } + } + } + else { + [Terminal.Gui.MessageBox]::ErrorQuery('Add-PSWorkitemCategory', 'A category name is required', @('Ok')) + } + + }) + $btnCancel = [Terminal.Gui.Button]@{ + X = 23 + Y = 6 + Width = 10 + Height = 1 + Text = 'Cancel' + } + $btnCancel.Add_Clicked({ + UpdateStatusTime + $subWin.RequestStop() + }) + + $subWin.Add($chkWhatIf) + $subWin.Add($chkForce) + $subWin.Add($lblDescription) + $subWin.Add($txtDescription) + $subWin.Add($lblCategory) + $subWin.Add($txtCategory) + $subWin.Add($btnCancel) + $subWin.Add($btnOk) + #set tab order + $txtCategory.TabIndex = 0 + $txtDescription.TabIndex = 1 + $chkWhatIf.TabIndex = 2 + $chkForce.TabIndex = 3 + $btnOk.TabIndex = 4 + $btnCancel.TabIndex = 5 + $txtCategory.SetFocus() + + [Terminal.Gui.Application]::Run($subWin) + [Terminal.Gui.Application]::Refresh() + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" +} + +Function RemoveCategory { + [CmdletBinding()] + Param() + + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" + $cs = [Terminal.Gui.ColorScheme]::New() + $cs.Normal = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::Black, [Terminal.Gui.Color]::Gray) + $cs.Focus = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::White, [Terminal.Gui.Color]::DarkGray) + $cs.HotNormal = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::BrightBlue, [Terminal.Gui.Color]::Gray) + $subWin = [Terminal.Gui.Dialog]@{ + Title = 'Remove Category' + X = [Terminal.Gui.Pos]::Center() + Y = [Terminal.Gui.Pos]::Center() + Width = 50 + Height = 10 + ColorScheme = $cs + } + + $lblCategory = [Terminal.Gui.Label]@{ + X = 1 + Y = 1 + Width = 10 + Height = 1 + Text = 'Category' + TabStop = $False + } + + $subDropCategory = [Terminal.Gui.ListView]@{ + Width = 25 + Height = 1 + X = $lblCategory.Frame.Width + 3 + Y = $lblCategory.Y + TabIndex = 1 + TabStop = $True + AllowsMultipleSelection = $False + CanFocus = $True + } + + $chkWhatIf = [Terminal.Gui.CheckBox]@{ + X = 1 + Y = 3 + Width = 10 + Height = 1 + Text = 'WhatIf' + } + $btnOk = [Terminal.Gui.Button]@{ + X = 13 + Y = 4 + Width = 10 + Height = 1 + Text = 'Ok' + } + $btnOK.Add_Clicked({ + if ($subDropCategory.Source.ToList()[$subDropCategory.SelectedItem] -match '\w+') { + + if ($chkWhatIf.Checked) { + $msg = @" + +Category = $($subDropCategory.Source.ToList()[$subDropCategory.SelectedItem]) + +Path = $($txtPath.Text.ToString()) +"@ + [Terminal.Gui.MessageBox]::Query('Remove-PSWorkitemCategory -WhatIf', $msg, @('Ok')) + } + else { + $splat = @{ + Category = $subDropCategory.Source.ToList()[$subDropCategory.SelectedItem] + Path = $txtPath.Text.ToString() + ErrorAction = 'Stop' + WarningVariable = 'warn' + } + + Try { + Remove-PSWorkItemCategory @splat + if ($warn) { + [Terminal.Gui.MessageBox]::ErrorQuery('Warning', $warn.message) + } + else { + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Removed category successfully" + #refresh the main form list + RefreshCategoryList + UpdateStatusTime + $subWin.RequestStop() + } + + } + Catch { + [Terminal.Gui.MessageBox]::ErrorQuery('Error', $_.Exception.Message) + } + } } else { - $lblOverDue.Visible = $False + [Terminal.Gui.MessageBox]::ErrorQuery('Remove-PSWorkitemCategory', 'A category name is required', @('Ok')) } - If ($item.Description -match "\w+") { - $chkClearDescription.Visible = $True + }) + $btnCancel = [Terminal.Gui.Button]@{ + X = 23 + Y = 4 + Width = 10 + Height = 1 + Text = 'Cancel' + } + $btnCancel.Add_Clicked({ + UpdateStatusTime + $subWin.RequestStop() + }) + + $subWin.Add($chkWhatIf) + $subWin.Add($lblCategory) + $subWin.Add($subDropCategory) + $subWin.Add($btnCancel) + $subWin.Add($btnOk) + #set tab order + $subDropCategory.TabIndex = 0 + $chkWhatIf.TabIndex = 1 + $btnOk.TabIndex = 2 + $btnCancel.TabIndex = 3 + $dropCategory.SetFocus() + #populate drop down list + $src = (Get-PSWorkItemCategory -Path $txtPath.Text.ToString()).Category | Sort-Object + $subDropCategory.SetSource($src) + $subDropCategory.SetNeedsDisplay() + $subDropCategory.SelectedItem = 0 + + [Terminal.Gui.Application]::Run($subWin) + + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" +} + +Function SetCategory { + [CmdletBinding()] + Param() + + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Starting $($MyInvocation.MyCommand)" + + #cache current categories + $catHash = Get-PSWorkItemCategory -Path $txtPath.Text.ToString() | Group-Object -Property Category -AsHashTable -AsString + + $cs = [Terminal.Gui.ColorScheme]::New() + $cs.Normal = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::Black, [Terminal.Gui.Color]::Gray) + $cs.Focus = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::White, [Terminal.Gui.Color]::DarkGray) + $cs.HotNormal = [Terminal.Gui.Attribute]::New([Terminal.Gui.Color]::BrightBlue, [Terminal.Gui.Color]::Gray) + $subWin = [Terminal.Gui.Dialog]@{ + Title = 'Set Category' + X = [Terminal.Gui.Pos]::Center() + Y = [Terminal.Gui.Pos]::Center() + Width = 50 + Height = 10 + ColorScheme = $cs + } + + $lblCategory = [Terminal.Gui.Label]@{ + X = 1 + Y = 1 + Width = 10 + Height = 1 + Text = 'Category' + TabStop = $False + } + + $subDropCategory = [Terminal.Gui.ListView]@{ + Width = 25 + Height = 1 + X = $lblCategory.Frame.Width + 3 + Y = $lblCategory.Y + TabIndex = 1 + TabStop = $True + AllowsMultipleSelection = $False + CanFocus = $True + } + + $subDropCategory.Add_SelectedItemChanged({ + $cat = $subDropCategory.Source.ToList()[$subDropCategory.SelectedItem] + $txtDescription.Text = $catHash[$cat].Description + }) + + $lblDescription = [Terminal.Gui.Label]@{ + X = 1 + Y = 3 + Width = 10 + Height = 1 + Text = 'Description' + TabStop = $False + } + $txtDescription = [Terminal.Gui.TextField]@{ + X = $lblDescription.Frame.Width +2 + Y = 3 + Width = 30 + Height = 1 + } + + $lblNewName = [Terminal.Gui.Label]@{ + X = 1 + Y = 5 + Width = 10 + Height = 1 + Text = 'New name' + TabStop = $False + } + $txtNewName = [Terminal.Gui.TextField]@{ + X = $lblNewName.Frame.Width +3 + Y = 5 + Width = 30 + Height = 1 + } + + $chkWhatIf = [Terminal.Gui.CheckBox]@{ + X = 1 + Y = 7 + Width = 10 + Height = 1 + Text = 'WhatIf' + } + $btnOk = [Terminal.Gui.Button]@{ + X = 13 + Y = $chkWhatIf.Y + Width = 10 + Height = 1 + Text = 'Ok' + } + $btnOK.Add_Clicked({ + if ($subDropCategory.Source.ToList()[$subDropCategory.SelectedItem] -match '\w+') { + if ($chkWhatIf.Checked) { + $msg = @" + +Category = $($subDropCategory.Source.ToList()[$subDropCategory.SelectedItem]) +Description = $($txtDescription.Text.ToString()) +New Name = $($txtNewName.Text.ToString()) +Path = $($txtPath.Text.ToString()) +"@ + [Terminal.Gui.MessageBox]::Query('Set-PSWorkItemCategory -WhatIf', $msg, @('Ok')) + } + else { + $splat = @{ + Category = $subDropCategory.Source.ToList()[$subDropCategory.SelectedItem] + Path = $txtPath.Text.ToString() + ErrorAction = 'Stop' + WarningVariable = 'warn' + } + if ($txtNewName.Text.ToString() -match "\w+") { + $splat.Add("NewName",$txtNewName.Text.ToString()) + } + if ($txtDescription.Text.ToString() -match "\w+") { + $splat.Add("Description",$txtDescription.Text.ToString()) + } + + Try { + $splat | out-string | out-file c:\temp\v.txt + Set-PSWorkItemCategory @splat -verbose 4>>c:\temp\v.txt + if ($warn) { + [Terminal.Gui.MessageBox]::ErrorQuery('Warning', $warn.message) + } + else { + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Changed category successfully" + #refresh the main form list + RefreshCategoryList + UpdateStatusTime + $subWin.RequestStop() + } + } + Catch { + [Terminal.Gui.MessageBox]::ErrorQuery('Error', $_.Exception.Message) + } + } } else { - $chkClearDescription.Visible = $False + [Terminal.Gui.MessageBox]::ErrorQuery('Remove-PSWorkitemCategory', 'A category name is required', @('Ok')) } - $txtTaskName.Text = $item.Name - $txtDueDate.Text = '{0:g}' -f $item.DueDate - $radioGrp.SelectedItem = 1 - $txtDays.Enabled = $False - $txtDescription.Text = $item.Description - $dropCategory.SelectedItem = $script:CatList.FindIndex({ $args -eq $item.Category }) - $txtProgress.Text = $item.Progress - -} \ No newline at end of file + }) + $btnCancel = [Terminal.Gui.Button]@{ + X = 23 + Y = $btnOk.Y + Width = 10 + Height = 1 + Text = 'Cancel' + } + $btnCancel.Add_Clicked({ + UpdateStatusTime + $subWin.RequestStop() + }) + + $subWin.Add($chkWhatIf) + $subWin.Add($lblDescription) + $subWin.Add($txtDescription) + $subWin.Add($lblCategory) + $subWin.Add($subDropCategory) + $subWin.Add($lblNewName) + $subWin.add($txtNewName) + $subWin.Add($btnCancel) + $subWin.Add($btnOk) + #set tab order + $subDropCategory.TabIndex = 0 + $txtDescription.TabIndex = 1 + $txtNewName.TabIndex = 2 + $chkWhatIf.TabIndex = 3 + $btnOk.TabIndex = 4 + $btnCancel.TabIndex = 5 + $dropCategory.SetFocus() + #populate drop down list + $src = (Get-PSWorkItemCategory -Path $txtPath.Text.ToString()).Category | Sort-Object + $subDropCategory.SetSource($src) + $subDropCategory.SetNeedsDisplay() + $subDropCategory.SelectedItem = 0 + + [Terminal.Gui.Application]::Run($subWin) + + Write-Verbose "[$((Get-Date).TimeOfDay) PRIVATE] Ending $($MyInvocation.MyCommand)" +} diff --git a/functions/public/Add-PSWorkItemCategory.ps1 b/functions/public/Add-PSWorkItemCategory.ps1 index 9dec140..8aa3f67 100644 --- a/functions/public/Add-PSWorkItemCategory.ps1 +++ b/functions/public/Add-PSWorkItemCategory.ps1 @@ -40,6 +40,7 @@ Function Add-PSWorkItemCategory { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) Write-Debug "Using bound parameters" $PSBoundParameters | Out-String | Write-Debug diff --git a/functions/public/Complete-PSWorkItem.ps1 b/functions/public/Complete-PSWorkItem.ps1 index d2178fa..069d68f 100644 --- a/functions/public/Complete-PSWorkItem.ps1 +++ b/functions/public/Complete-PSWorkItem.ps1 @@ -34,7 +34,7 @@ Function Complete-PSWorkItem { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) - + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) Write-Debug "[$((Get-Date).TimeOfDay) BEGIN ] $($MyInvocation.MyCommand): PSBoundParameters" $PSBoundParameters | Out-String | Write-Debug diff --git a/functions/public/Get-PSWorkItem.ps1 b/functions/public/Get-PSWorkItem.ps1 index 63af891..5d50d4e 100644 --- a/functions/public/Get-PSWorkItem.ps1 +++ b/functions/public/Get-PSWorkItem.ps1 @@ -85,6 +85,7 @@ Function Get-PSWorkItem { $PSDefaultParameterValues['_verbose:block'] = 'Begin' _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) _verbose ($strings.DetectedCulture -f (Get-Culture)) } #begin diff --git a/functions/public/Get-PSWorkItemArchive.ps1 b/functions/public/Get-PSWorkItemArchive.ps1 index d1e42a3..b7ce8ab 100644 --- a/functions/public/Get-PSWorkItemArchive.ps1 +++ b/functions/public/Get-PSWorkItemArchive.ps1 @@ -32,45 +32,46 @@ Function Get-PSWorkItemArchive { ) DynamicParam { # Added 26 Sept 2023 to support dynamic categories based on path - if (-Not $PSBoundParameters.ContainsKey("Path")) { - $Path = $global:PSWorkItemPath - } - If (Test-Path $Path) { + if (-Not $PSBoundParameters.ContainsKey("Path")) { + $Path = $global:PSWorkItemPath + } + If (Test-Path $Path) { - $paramDictionary = New-Object -Type System.Management.Automation.RuntimeDefinedParameterDictionary + $paramDictionary = New-Object -Type System.Management.Automation.RuntimeDefinedParameterDictionary - # Defining parameter attributes - $attributeCollection = New-Object -Type System.Collections.ObjectModel.Collection[System.Attribute] - $attributes = New-Object System.Management.Automation.ParameterAttribute - $attributes.ParameterSetName = 'Category' - $attributes.HelpMessage = 'Get all archived PSWorkItems by category' + # Defining parameter attributes + $attributeCollection = New-Object -Type System.Collections.ObjectModel.Collection[System.Attribute] + $attributes = New-Object System.Management.Automation.ParameterAttribute + $attributes.ParameterSetName = 'Category' + $attributes.HelpMessage = 'Get all archived PSWorkItems by category' - # Adding ValidateSet parameter validation - #only get categories used in the Archive table - #It is possible categories might be entered in different cases in the database - [string[]]$values = (Get-PSWorkItemData -Table Archive -Path $Path).Category | - Foreach-Object { [CultureInfo]::CurrentCulture.TextInfo.ToTitleCase($_)} | - Select-Object -unique | Sort-Object - $v = New-Object System.Management.Automation.ValidateSetAttribute($values) - $AttributeCollection.Add($v) + # Adding ValidateSet parameter validation + #only get categories used in the Archive table + #It is possible categories might be entered in different cases in the database + [string[]]$values = (Get-PSWorkItemData -Table Archive -Path $Path).Category | + Foreach-Object { [CultureInfo]::CurrentCulture.TextInfo.ToTitleCase($_)} | + Select-Object -unique | Sort-Object + $v = New-Object System.Management.Automation.ValidateSetAttribute($values) + $AttributeCollection.Add($v) - # Adding ValidateNotNullOrEmpty parameter validation - $v = New-Object System.Management.Automation.ValidateNotNullOrEmptyAttribute - $AttributeCollection.Add($v) - $attributeCollection.Add($attributes) + # Adding ValidateNotNullOrEmpty parameter validation + $v = New-Object System.Management.Automation.ValidateNotNullOrEmptyAttribute + $AttributeCollection.Add($v) + $attributeCollection.Add($attributes) - # Defining the runtime parameter - $dynParam1 = New-Object -Type System.Management.Automation.RuntimeDefinedParameter('Category', [String], $attributeCollection) - $paramDictionary.Add('Category', $dynParam1) + # Defining the runtime parameter + $dynParam1 = New-Object -Type System.Management.Automation.RuntimeDefinedParameter('Category', [String], $attributeCollection) + $paramDictionary.Add('Category', $dynParam1) - return $paramDictionary - } # end if + return $paramDictionary + } # end if } #end DynamicParam Begin { $PSDefaultParameterValues["_verbose:Command"] = $MyInvocation.MyCommand $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) } #begin diff --git a/functions/public/Get-PSWorkItemData.ps1 b/functions/public/Get-PSWorkItemData.ps1 index a3fe18e..2274964 100644 --- a/functions/public/Get-PSWorkItemData.ps1 +++ b/functions/public/Get-PSWorkItemData.ps1 @@ -23,6 +23,7 @@ Function Get-PSWorkItemData { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) Write-Debug "Using bound parameters" $PSBoundParameters | Out-String | Write-Debug diff --git a/functions/public/Get-PSWorkItemDatabase.ps1 b/functions/public/Get-PSWorkItemDatabase.ps1 index a76d8bb..d3a2b30 100644 --- a/functions/public/Get-PSWorkItemDatabase.ps1 +++ b/functions/public/Get-PSWorkItemDatabase.ps1 @@ -17,6 +17,7 @@ Function Get-PSWorkItemDatabase { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) } #begin diff --git a/functions/public/Get-PSWorkItemPreferences.ps1 b/functions/public/Get-PSWorkItemPreferences.ps1 index c6282f0..7fa289e 100644 --- a/functions/public/Get-PSWorkItemPreferences.ps1 +++ b/functions/public/Get-PSWorkItemPreferences.ps1 @@ -8,6 +8,7 @@ Function Get-PSWorkItemPreference { $PSDefaultParameterValues['_verbose:block'] = 'Begin' _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) $PrefPath = Join-Path -Path $HOME -ChildPath .psworkitempref.json } #begin diff --git a/functions/public/Get-PSWorkItemReport.ps1 b/functions/public/Get-PSWorkItemReport.ps1 index 664d76f..6d02e4c 100644 --- a/functions/public/Get-PSWorkItemReport.ps1 +++ b/functions/public/Get-PSWorkItemReport.ps1 @@ -17,6 +17,7 @@ Function Get-PSWorkItemReport { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) } #begin diff --git a/functions/public/Get-PSWorkitemCategory.ps1 b/functions/public/Get-PSWorkitemCategory.ps1 index aaf0c8a..4b15bc9 100644 --- a/functions/public/Get-PSWorkitemCategory.ps1 +++ b/functions/public/Get-PSWorkitemCategory.ps1 @@ -59,6 +59,7 @@ Function Get-PSWorkItemCategory { $PSDefaultParameterValues['_verbose:block'] = 'Begin' _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) Write-Debug 'Using bound parameters' $PSBoundParameters | Out-String | Write-Debug diff --git a/functions/public/Initialize-PSWorkItemDatabase.ps1 b/functions/public/Initialize-PSWorkItemDatabase.ps1 index 09ffcc7..e3bc1a5 100644 --- a/functions/public/Initialize-PSWorkItemDatabase.ps1 +++ b/functions/public/Initialize-PSWorkItemDatabase.ps1 @@ -22,6 +22,7 @@ Function Initialize-PSWorkItemDatabase { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) } #begin Process { diff --git a/functions/public/New-PSWorkItem.ps1 b/functions/public/New-PSWorkItem.ps1 index f901987..fe11f73 100644 --- a/functions/public/New-PSWorkItem.ps1 +++ b/functions/public/New-PSWorkItem.ps1 @@ -99,6 +99,7 @@ Function New-PSWorkItem { $PSDefaultParameterValues['_verbose:block'] = 'Begin' _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) Try { $conn = Open-MySQLiteDB -Path $Path -ErrorAction Stop diff --git a/functions/public/Open-PSWorkItemConsole.ps1 b/functions/public/Open-PSWorkItemConsole.ps1 index 13bbe35..1a9b556 100644 --- a/functions/public/Open-PSWorkItemConsole.ps1 +++ b/functions/public/Open-PSWorkItemConsole.ps1 @@ -71,7 +71,13 @@ Function Open-PSWorkItemConsole { $MenuBarItem1 = [Terminal.Gui.MenuBarItem]::New('_Help', @($MenuItem4, $MenuItem7,$MenuItem5, $MenuItem6, $MenuItem3)) - $MenuBar = [Terminal.Gui.MenuBar]::New(@($MenuBarItem0, $MenuBarItem1)) + #3 Oct 2023 - add menu bar to manage categories + $MenuItem8 = [Terminal.Gui.MenuItem]::New('Add Category', '', { AddCategory }) + $MenuItem9 = [Terminal.Gui.MenuItem]::New('Remove Category', '', { RemoveCategory }) + $MenuItem10 = [Terminal.Gui.MenuItem]::New('Set Category', '', { SetCategory }) + $MenuBarItem2 = [Terminal.Gui.MenuBarItem]::New('_Categories', @($MenuItem8, $MenuItem10,$MenuItem9)) + + $MenuBar = [Terminal.Gui.MenuBar]::New(@($MenuBarItem0, $MenuBarItem2,$MenuBarItem1)) $Window.Add($MenuBar) @@ -174,7 +180,7 @@ Function Open-PSWorkItemConsole { $dropCategory.Add_SelectedItemChanged({ if ($chkFilterTable.Checked) { - RefreshTable -FilterCategory $script:CatList[$dropCategory.SelectedItem] + RefreshTable -FilterCategory $dropCategory.Source.ToList()[$dropCategory.SelectedItem] } }) @@ -264,7 +270,7 @@ Function Open-PSWorkItemConsole { $chkFilterTable.Add_Toggled({ if ($chkFilterTable.Checked) { - RefreshTable -FilterCategory $script:CatList[$dropCategory.SelectedItem] + RefreshTable -FilterCategory $dropCategory.Source.ToList()[$dropCategory.SelectedItem] } else { RefreshTable @@ -282,51 +288,52 @@ Function Open-PSWorkItemConsole { } $btnAdd.Add_Clicked({ - if ($txtTaskName.Text.ToString() -match '\w+') { - if ($chkWhatIf.Checked) { - ShowWhatIf -Command New - Return - } - $r = @{ - Name = $txtTaskName.Text.ToString() - Category = $script:CatList[$dropCategory.SelectedItem] - Path = $txtPath.Text.ToString() - ErrorAction = 'Stop' - } - if ($txtDescription.text.ToString() -match '\w+') { - $r.Add('Description', $txtDescription.text.ToString()) - } - - if ($txtDays.Enabled) { - $r.Add('DaysDue', $txtDays.Text.ToString()) - } - else { - $r.Add('DueDate', $txtDueDate.Text.ToString()) - } + if ($txtTaskName.Text.ToString() -match '\w+') { + if ($chkWhatIf.Checked) { + ShowWhatIf -Command New + Return + } + $r = @{ + Name = $txtTaskName.Text.ToString() + Category = $dropCategory.Source.ToList()[$dropCategory.SelectedItem] + Path = $txtPath.Text.ToString() + ErrorAction = 'Stop' + } + if ($txtDescription.text.ToString() -match '\w+') { + $r.Add('Description', $txtDescription.text.ToString()) + } - $StatusBar.Items[3].Title = "Creating PSWorkItem $($txtTaskName.Text.ToString()) in $($r.Path)" - $StatusBar.SetChildNeedsDisplay() - [Terminal.Gui.Application]::Refresh() - Start-Sleep -Milliseconds 1000 - Try { - New-PSWorkItem @r - ClearForm - RefreshTable - [Terminal.Gui.Application]::Refresh() - } - Catch { - [Terminal.Gui.MessageBox]::ErrorQuery('Error', $_.Exception.Message) - } + if ($txtDays.Enabled) { + $r.Add('DaysDue', $txtDays.Text.ToString()) } else { - $StatusBar.Items[3].Title = 'Oops! You forgot to specify a name for your PSWorkItem.' - $StatusBar.SetChildNeedsDisplay() - [Terminal.Gui.Application]::Refresh() - Start-Sleep -Milliseconds 2000 - $StatusBar.Items[3].Title = 'Ready' + $r.Add('DueDate', $txtDueDate.Text.ToString()) + } + + $StatusBar.Items[3].Title = "Creating PSWorkItem $($txtTaskName.Text.ToString()) in $($r.Path)" + $StatusBar.SetChildNeedsDisplay() + [Terminal.Gui.Application]::Refresh() + Start-Sleep -Milliseconds 1000 + Try { + New-PSWorkItem @r + ClearForm + UpdateReport + RefreshTable [Terminal.Gui.Application]::Refresh() } - }) + Catch { + [Terminal.Gui.MessageBox]::ErrorQuery('Error', $_.Exception.Message) + } + } + else { + $StatusBar.Items[3].Title = 'Oops! You forgot to specify a name for your PSWorkItem.' + $StatusBar.SetChildNeedsDisplay() + [Terminal.Gui.Application]::Refresh() + Start-Sleep -Milliseconds 2000 + $StatusBar.Items[3].Title = 'Ready' + [Terminal.Gui.Application]::Refresh() + } + }) $controls += $btnSet = [Terminal.Gui.Button]@{ X = $btnAdd.Frame.Width + 2 @@ -365,7 +372,7 @@ Function Open-PSWorkItemConsole { $r = @{ ID = $TableView.table.rows[$TableView.SelectedRow].ID Name = $txtTaskName.Text.ToString() - Category = $script:CatList[$dropCategory.SelectedItem] + Category = $dropCategory.Source.ToList()[$dropCategory.SelectedItem] Path = $txtPath.Text.ToString() ErrorAction = 'Stop' } @@ -392,6 +399,7 @@ Function Open-PSWorkItemConsole { Set-PSWorkItem @r Populate RefreshTable + UpdateReport $StatusBar.Items[3].Title = "Ready" $StatusBar.SetChildNeedsDisplay() [Terminal.Gui.Application]::Refresh() @@ -437,6 +445,7 @@ Function Open-PSWorkItemConsole { Try { Complete-PSWorkItem @r ClearForm + UpdateReport RefreshTable [Terminal.Gui.Application]::Refresh() } @@ -488,6 +497,7 @@ Function Open-PSWorkItemConsole { [Terminal.Gui.MessageBox]::ErrorQuery('Error', $_.Exception.Message) } ClearForm + UpdateReport RefreshTable [Terminal.Gui.Application]::Refresh() } @@ -522,9 +532,39 @@ Function Open-PSWorkItemConsole { $TableView.Style.ShowHorizontalHeaderUnderline = $True $TableView.Style.ShowVerticalHeaderLines = $False - #event handler + #event handlers $TableView.Add_SelectedCellChanged({Populate}) + $TableView.Add_MouseClick({ + Param ($Mouse) + + $item = $TableView.table.rows[$TableView.SelectedRow] + + if ($Mouse.mouseEvent.Flags -eq [Terminal.Gui.MouseFlags]::Button3Clicked) { + $Detail = Get-PSWorkItem -Path $txtPath.Text.ToString() -ID $item.ID | + Select-Object -Property ID,Overdue,Description,Progress,Category,TaskCreated,TaskModified,Age,Due,TimeRemaining | + Out-String + + $DetailDialog = [Terminal.Gui.Dialog]@{ + Title = $item.name + X = [Terminal.Gui.Pos]::Center() + Y = [Terminal.Gui.Pos]::Center() + Width = 50 + Height = 20 + TextAlignment = 'Left' + Text = $Detail + } + $ok = [Terminal.Gui.Button]@{ + Text = 'OK' + } + $ok.Add_Clicked({ $DetailDialog.RequestStop() }) + $DetailDialog.AddButton($ok) + + [Terminal.Gui.Application]::Run($DetailDialog) + } + + }) + $window.Add($TableView) #endregion @@ -550,6 +590,7 @@ Function Open-PSWorkItemConsole { #refresh data RefreshTable RefreshCategoryList + UpdateReport $txtTaskName.SetFocus() #set a timer to update the status bar every 15 seconds $TimerToken = [Terminal.Gui.Application]::MainLoop.AddTimeout((New-TimeSpan -Seconds 15), { UpdateStatusTime }) diff --git a/functions/public/Remove-PSWorkItem.ps1 b/functions/public/Remove-PSWorkItem.ps1 index 7e1ad0e..065d6f9 100644 --- a/functions/public/Remove-PSWorkItem.ps1 +++ b/functions/public/Remove-PSWorkItem.ps1 @@ -28,6 +28,7 @@ Function Remove-PSWorkItem { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) Write-Debug "[$((Get-Date).TimeOfDay) BEGIN ] $($MyInvocation.MyCommand): PSBoundParameters" $PSBoundParameters | Out-String | Write-Debug diff --git a/functions/public/Remove-PSWorkItemArchive.ps1 b/functions/public/Remove-PSWorkItemArchive.ps1 index ff11647..c20551f 100644 --- a/functions/public/Remove-PSWorkItemArchive.ps1 +++ b/functions/public/Remove-PSWorkItemArchive.ps1 @@ -75,6 +75,7 @@ Function Remove-PSWorkItemArchive { $PSDefaultParameterValues['_verbose:block'] = 'Begin' _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) Write-Debug "[$((Get-Date).TimeOfDay) BEGIN ] $($MyInvocation.MyCommand): PSBoundParameters" $PSBoundParameters | Out-String | Write-Debug diff --git a/functions/public/Remove-PSWorkItemCategory.ps1 b/functions/public/Remove-PSWorkItemCategory.ps1 index 95009e7..ad099cf 100644 --- a/functions/public/Remove-PSWorkItemCategory.ps1 +++ b/functions/public/Remove-PSWorkItemCategory.ps1 @@ -2,7 +2,6 @@ Function Remove-PSWorkItemCategory { [cmdletbinding(SupportsShouldProcess)] [OutputType("None")] Param( - [Parameter( HelpMessage = 'The path to the PSWorkItem SQLite database file. It must end in .db' )] @@ -60,6 +59,7 @@ Function Remove-PSWorkItemCategory { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) Write-Debug "Using bound parameters" $PSBoundParameters | Out-String | Write-Debug @@ -75,15 +75,20 @@ Function Remove-PSWorkItemCategory { Process { $PSDefaultParameterValues["_verbose:block"] = "Process" + $Category = $PSBoundParameters['Category'] if ($conn.state -eq 'open') { foreach ($item in $Category ) { _verbose -message ($strings.RemoveCategory -f $item) $query = "DELETE FROM categories WHERE category = '$item'" + _verbose -message $query if ($PSCmdlet.ShouldProcess($item)) { Invoke-MySQLiteQuery -Query $query -Connection $conn -KeepAlive } } } + else { + Write-Warning $strings.DatabaseConnectionNotOpen + } } #process End { diff --git a/functions/public/Set-PSWorkItem.ps1 b/functions/public/Set-PSWorkItem.ps1 index 26d1527..e6c7164 100644 --- a/functions/public/Set-PSWorkItem.ps1 +++ b/functions/public/Set-PSWorkItem.ps1 @@ -59,42 +59,43 @@ Function Set-PSWorkItem { ) DynamicParam { # Added 26 Sept 2023 to support dynamic categories based on path - if (-Not $PSBoundParameters.ContainsKey("Path")) { - $Path = $global:PSWorkItemPath - } - If (Test-Path $Path) { - - $paramDictionary = New-Object -Type System.Management.Automation.RuntimeDefinedParameterDictionary - - # Defining parameter attributes - $attributeCollection = New-Object -Type System.Collections.ObjectModel.Collection[System.Attribute] - $attributes = New-Object System.Management.Automation.ParameterAttribute - $attributes.HelpMessage = 'Specify an updated category. You can run Get-PSWorkItemCategory to see the list.' - # Adding ValidateSet parameter validation - #It is possible categories might be entered in different cases in the database - [string[]]$values = (Get-PSWorkItemData -Table Categories -Path $Path).Category | - ForEach-Object { [CultureInfo]::CurrentCulture.TextInfo.ToTitleCase($_) } | - Select-Object -Unique | Sort-Object - $v = New-Object System.Management.Automation.ValidateSetAttribute($values) - $AttributeCollection.Add($v) - - # Adding ValidateNotNullOrEmpty parameter validation - $v = New-Object System.Management.Automation.ValidateNotNullOrEmptyAttribute - $AttributeCollection.Add($v) - $attributeCollection.Add($attributes) - - # Defining the runtime parameter - $dynParam1 = New-Object -Type System.Management.Automation.RuntimeDefinedParameter('Category', [String], $attributeCollection) - $paramDictionary.Add('Category', $dynParam1) - - return $paramDictionary - } # end if + if (-Not $PSBoundParameters.ContainsKey("Path")) { + $Path = $global:PSWorkItemPath + } + If (Test-Path $Path) { + + $paramDictionary = New-Object -Type System.Management.Automation.RuntimeDefinedParameterDictionary + + # Defining parameter attributes + $attributeCollection = New-Object -Type System.Collections.ObjectModel.Collection[System.Attribute] + $attributes = New-Object System.Management.Automation.ParameterAttribute + $attributes.HelpMessage = 'Specify an updated category. You can run Get-PSWorkItemCategory to see the list.' + # Adding ValidateSet parameter validation + #It is possible categories might be entered in different cases in the database + [string[]]$values = (Get-PSWorkItemData -Table Categories -Path $Path).Category | + ForEach-Object { [CultureInfo]::CurrentCulture.TextInfo.ToTitleCase($_) } | + Select-Object -Unique | Sort-Object + $v = New-Object System.Management.Automation.ValidateSetAttribute($values) + $AttributeCollection.Add($v) + + # Adding ValidateNotNullOrEmpty parameter validation + $v = New-Object System.Management.Automation.ValidateNotNullOrEmptyAttribute + $AttributeCollection.Add($v) + $attributeCollection.Add($attributes) + + # Defining the runtime parameter + $dynParam1 = New-Object -Type System.Management.Automation.RuntimeDefinedParameter('Category', [String], $attributeCollection) + $paramDictionary.Add('Category', $dynParam1) + + return $paramDictionary + } # end if } #end DynamicParam Begin { $PSDefaultParameterValues['_verbose:Command'] = $MyInvocation.MyCommand $PSDefaultParameterValues['_verbose:block'] = 'Begin' _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) Write-Debug "[$((Get-Date).TimeOfDay) BEGIN ] $($MyInvocation.MyCommand): PSBoundParameters" $PSBoundParameters | Out-String | Write-Debug diff --git a/functions/public/Set-PSWorkItemCategory.ps1 b/functions/public/Set-PSWorkItemCategory.ps1 index a379138..7e6ebbc 100644 --- a/functions/public/Set-PSWorkItemCategory.ps1 +++ b/functions/public/Set-PSWorkItemCategory.ps1 @@ -2,16 +2,6 @@ Function Set-PSWorkItemCategory { [cmdletbinding(SupportsShouldProcess)] [OutputType('None', 'PSWorkItemCategory')] Param( -<# [Parameter( - Position = 0, - Mandatory, - ValueFromPipeline, - HelpMessage = 'Specify a case-sensitive category name.' - )] - [ValidateNotNullOrEmpty()] - [Alias('Name')] - [string]$Category, #> - [Parameter( HelpMessage = 'Specify a category comment or description.' )] @@ -81,6 +71,7 @@ Function Set-PSWorkItemCategory { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) if ((-Not $PSBoundParameters.ContainsKey('Description')) -AND (-Not $PSBoundParameters.ContainsKey('NewName'))) { Write-Warning $strings.WarnDescriptionOrName Return @@ -111,6 +102,7 @@ Function Set-PSWorkItemCategory { Process { $PSDefaultParameterValues["_verbose:block"] = "Process" + $Category = $PSBoundParameters['Category'] _verbose -message ($strings.ProcessCategory -f $Category) if ($conn.state -eq 'open') { _verbose -message ($strings.ValidateCategory -f $category) diff --git a/functions/public/Update-PSWorkItemDatabase.ps1 b/functions/public/Update-PSWorkItemDatabase.ps1 index ecdb4c6..9c15ff5 100644 --- a/functions/public/Update-PSWorkItemDatabase.ps1 +++ b/functions/public/Update-PSWorkItemDatabase.ps1 @@ -29,6 +29,7 @@ Function Update-PSWorkItemDatabase { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) _verbose -message ($strings.UsingDB -f $path) $dbConnection = Open-MySQLiteDB -Path $Path diff --git a/functions/public/Update-PSWorkItemPreference.ps1 b/functions/public/Update-PSWorkItemPreference.ps1 index 78a72c0..8beb2d3 100644 --- a/functions/public/Update-PSWorkItemPreference.ps1 +++ b/functions/public/Update-PSWorkItemPreference.ps1 @@ -27,6 +27,7 @@ Function Update-PSWorkItemPreference { $PSDefaultParameterValues["_verbose:block"] = "Begin" _verbose -message $strings.Starting _verbose -message ($strings.PSVersion -f $PSVersionTable.PSVersion) + _verbose -message ($strings.UsingModule -f (Get-Command -name $MyInvocation.MyCommand).Version) $FilePath = Join-Path -Path $HOME -ChildPath ".psworkitempref.json" } #begin