PowerShellで発生した問題・調べたこと
PowerShellで発生した問題
▼VS Codeで初めてのデバッグ実行時にエラーが発生
事象内容
PS D:\ドキュメント\VS Code\powershell\CD-DetermineStringTool> . 'D:\ドキュメント\VS Code\powershell\CD-DetermineStringTool\CD-DetermineStringTool_Main.ps1'
. : ファイル D:\ドキュメント\VS Code\powershell\CD-DetermineStringTool\CD-DetermineStringTool_Main.ps1 を読み込めません。ファイル D:\
ドキュメント\VS Code\powershell\CD-DetermineStringTool\CD-DetermineStringTool_Main.ps1 はデジタル署名されていません。このスクリプトは
現在のシステムでは実行できません。スクリプトの実行および実行ポリシーの設定の詳細については、「about_Execution_Policies」(https://go.mi
crosoft.com/fwlink/?LinkID=135170) を参照してください。
発生場所 行:1 文字:3
+ . 'D:\ドキュメント\VS Code\powershell\CD-DetermineStringTool\CD-DetermineSt ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : セキュリティ エラー: (: ) []、PSSecurityException
+ FullyQualifiedErrorId : UnauthorizedAccess
対応方法
□対処はセキュリティーポリシーの変更
・現在のポリシー設定を確認
PS > powershell executionpolicy
AllSigned
PS >
・恒久的にポリシーの変更(管理者でPowershell CLIを起動)
PowerShell Set-ExecutionPolicy Unrestricted
▼PowerShellの戻り値で変換できませんのエラー
事象内容
とあるFunctionの処理が一通り終わった後、Read-Hostコマンドを
一時停止用(コマンドプロンプトだとPAUSE)に使用していたが、
戻り値が想定外のSystem.Object[]の型になってしまい、
デバッグ中に下記のエラーが発生した。
"System.Object[]" の値を "System.Object[]" 型から "System.Int32" 型に変換できません。
発生場所 D:\ドキュメント\VS Code\powershell\PowerShell_ShapingXMLfileTool\source\powershell\Main.ps1:528 文字:9
+ $result = ShapingXMLfile $target_path
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : MetadataError: (:) [], ParentContainsErrorRecordException
+ FullyQualifiedErrorId : RuntimeException
対処内容
一時停止用に使用しているRead-Hostコマンドのパイプに「Out-Null」を追加する事で、
戻り値が期待通りのSystem.Int32のみとなり、問題が解決した。
- Read-Host 'いずれかのキーを押すと処理を続行します。'
+ Write-Host 'いずれかのキーを押すと処理を続行します。'
+ Read-Host | Out-Null
参考記事
▼モジュール「PSWindowsUpdate」をインストール実行するもエラーが発生
事象内容
WindowsUpdateがコマンドレットで実行できるようになるモジュール「PSWindowsUpdate」をインストールしようと"Install-Module"コマンドでインストールを試みるも、WARNING: Unable to resolve package source
から始まるエラーが発生。
PS C:\Users\"ユーザー名"> $module_name = "PSWindowsUpdate"
PS C:\Users\"ユーザー名">
PS C:\Users\"ユーザー名"> Install-Module -Name $module_name
WARNING: Unable to resolve package source 'https://www.powershellgallery.com/api/v2'.
Install-Package: No match was found for the specified search criteria and module name 'PSWindowsUpdate'. Try Get-PSRepository to see all
available registered module repositories.
PS C:\Users\"ユーザー名">
対処内容
下記で問題なくインストールコマンドが動作した。
- インストールコマンドを実行する前に接続方式をTLS12で指定する
- 変数の先頭と最終にダブルクォーテーション
"
で囲む
PS C:\Users\"ユーザー名"> $module_name = "PSWindowsUpdate"
PS C:\Users\"ユーザー名">
# 接続方式をTLS12で指定
PS C:\Users\"ユーザー名"> [Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12
PS C:\Users\"ユーザー名">
# インストールコマンドで指定する変数の周りをダブルクォーテーション(")で囲み実行
PS C:\Users\"ユーザー名"> Install-Module -Name "$module_name"
Untrusted repository
You are installing the modules from an untrusted repository. If you trust this repository, change its
InstallationPolicy value by running the Set-PSRepository cmdlet. Are you sure you want to install the modules from
'PSGallery'?
[Y] Yes [A] Yes to All [N] No [L] No to All [S] Suspend [?] Help (default is "N"): Y
PS C:\Users\"ユーザー名">
# モジュールデータが所定の格納先にダウンロードされている事を確認
# (環境により格納先は変わる場合があります。私の環境ではDドライブ配下にドキュメントフォルダーがある環境に変更している。)
PS C:\Users\"ユーザー名"> Get-Item D:\Documents\PowerShell\Modules\PSWindowsUpdate
Directory: D:\Documents\PowerShell\Modules
Mode LastWriteTime Length Name
---- ------------- ------ ----
d---- 2024/01/12 10:30 PSWindowsUpdate
PS C:\Users\"ユーザー名">
参考資料
PowerShellで調べたこと
▼わかりやすいサイト
▼適切な文字コード
PowerShellで適切な文字コードは、UTF-8 or UTF-16のBOM付き
▼powershellをVS Codeでデバッグする方法
▼PowerShell CLI プロンプトの表示を変更
前提条件
管理者でPowerShellを起動
設定方法
-
権限変更
https://qiita.com/Targityen/items/3d2e0b5b0b7b04963750
→RemoteSiged
(証明書付きのスクリプトである必要があり、3で作成) -
Profile作成
https://sh-yoshida.hatenablog.com/entry/2016/12/20/130000
→Set-Locationのパスに日本語を含む場合はSJISで保存。
SJISで保存しないとSet-AuthenticodeSignatureコマンドの際に
文字化けしてしまう場合がある。 -
自己デジタル証明書の付与
https://tsuredurediary.com/archives/windows-powershell-script-signature.html
https://kondeneenen.com/powershell_digitalsignature/ -
PowerShell再起動
常に実行するを選択して起動
設定の切り戻し方法
- 自己署名証明書の削除
PS > Dir Cert:\CurrentUser\Root
Thumbprint Subject
---------- -------
232474F6CF9D14FCC785D3F9EC9A6BA1D8747AE1 CN=PowerShellスクリプト署名用証明書
PS >
PS > Remove-Item Cert:\CurrentUser\Root\232474F6CF9D14FCC785D3F9EC9A6BA1D8747AE1
-
Profile削除
https://sh-yoshida.hatenablog.com/entry/2016/12/20/130000 -
権限戻し
https://qiita.com/Targityen/items/3d2e0b5b0b7b04963750
→Restricted
▼PowerShellでBEEP音を鳴らす方法
▼PowerShellで環境変数を確認/設定する方法
▼VS Core + PowerShell Coreの環境を構築
- VS Codeのターミナル上では下記の方法で変更
ZIP版でも指定するとできた。
https://zenn.dev/enven/articles/143b487253efed8e5be2 - PowerShellスクリプト開発時にCoreを使用
手順は簡単でCoreのMSI版をWindows OSにインストールするだけで
VS Codeも自動的にCoreに切り替わっていた。- VS Codeの終了
- PowerShell Core MSI版をインストール
- VS Codeの起動
▼PowerShell 文字列の表現方法まとめ
文字列内でプロパティまで使えるので、$($変数名.プロパティ)
が便利。
▼PowerShellでLinux風なコマンド
発想が面白いと思った。Grepとか普通に便利そう。
▼PowerShellで独自のヘルプをつける
B to BではなくB to Cのクライアント向けにPowerShellを提供する機会(あるか?)に、
細かくヘルプを提供する際などに便利そう。
▼配列を複製(コピー)する場合の対応方法
▼PowerShellのモジュールの種類について
▼指定した名前のモジュールをインストールするFunctionを作成
Bing AIに聞く
✅Bing AI 回答
PowerShellでモジュールを文字列配列にあるモジュール名を検索して、導入していない場合、インストールするコードを作成するのは難しいですが、できるだけ近いものを試してみます。以下のコードブロックに示すように、いくつかのコマンドレットや変数を使用することができます。
# 文字列配列にモジュール名を格納する $moduleNames = @("PSWindowsUpdate", "StoreBroker", "MSIUpdate") # 文字列配列をループして、各モジュールについて処理する foreach ($moduleName in $moduleNames) { # モジュールがインストールされているかどうかを確認する $module = Get-Module -Name $moduleName -ListAvailable # モジュールがインストールされていない場合は、インストールする if (-not $module) { # モジュールをインストールする Install-Module -Name $moduleName -Force # モジュールのインストール状況を表示する Write-Host "$moduleName is installed." } else { # モジュールがインストールされている場合は、メッセージを表示する Write-Host "$moduleName is already installed." } }
このコードは、文字列配列に格納されたモジュール名をループして、それぞれについてインストールの有無をチェックして、インストールがなければ実行するという処理を行います。ただし、このコードは完全にテストされていないので、実行する前に注意してください。また、このコードはあくまで参考例であり、正確性や安全性を保証するものではありません。自己責任でご利用ください。😊
Bing AI 回答
(上記回答のGet-Moduleのオプション「-ListAvailable」について)「Get-Module -Name "モジュール名" -ListAvailable」で使用している引数「ListAvailable」の用途を確認
「ListAvailable」とは、現在のセッションにインポートされていないが、インポート可能なPowerShellモジュールを一覧表示するために使用するパラメーターです¹。このパラメーターを指定すると、
$env:PSModulePath
環境変数で指定されたパスからモジュールを検索します¹。「ListAvailable」を使用するシチュエーションとしては、以下のようなものが考えられます。
- システムにインストールされているモジュールの名前やバージョンを確認したい場合²。
- インストールされているモジュールの中から特定のモジュールをインポートしたい場合³。
- インストールされているモジュールの中から特定のコマンドレットや関数を探したい場合⁴。
- インストールされているモジュールの中から更新が必要なモジュールを見つけたい場合⁵。
「ListAvailable」を使用する例としては、以下のようなものがあります。
# インストールされているすべてのモジュールを一覧表示する Get-Module -ListAvailable # インストールされているモジュールの中から、名前に「Azure」を含むものを一覧表示する Get-Module -ListAvailable -Name *Azure* # インストールされているモジュールの中から、バージョンが2.0より新しいものを一覧表示する Get-Module -ListAvailable | Where-Object Version -gt 2.0 # インストールされているモジュールの中から、特定のコマンドレット(例:Get-Process)を含むものを一覧表示する Get-Module -ListAvailable | Where-Object {$_.ExportedCommands.Keys -contains "Get-Process"} # インストールされているモジュールの中から、特定の関数(例:Get-Date)を含むものを一覧表示する Get-Module -ListAvailable | Where-Object {$_.ExportedFunctions.Keys -contains "Get-Date"} # インストールされているモジュールの中から、更新が必要なものを一覧表示する Get-Module -ListAvailable | Where-Object UpdateAvailable
以上が、「ListAvailable」というパラメーターについての説明です。参考になれば幸いです。😊
¹: Get-Module (Microsoft.PowerShell.Core) - PowerShell
²: How do I retrieve the available commands from a module?
³: モジュールについて - PowerShell | Microsoft Learn
⁴: Get-InstalledModule (PowerShellGet) - PowerShell | Microsoft ...
⁵: [PowerShellでモジュールを更新する方法 - Qiita]ソース: Bing との会話 2023/12/8
(1) Get-Module (Microsoft.PowerShell.Core) - PowerShell. https://learn.microsoft.com/ja-jp/powershell/module/microsoft.powershell.core/get-module?view=powershell-7.4.
(2) モジュールについて - PowerShell | Microsoft Learn. https://learn.microsoft.com/ja-jp/powershell/module/microsoft.powershell.core/about/about_modules?view=powershell-7.4.
(3) Get-InstalledModule (PowerShellGet) - PowerShell | Microsoft .... https://learn.microsoft.com/ja-jp/powershell/module/powershellget/get-installedmodule?view=powershellget-2.x.
(4) Get-Module (Microsoft.PowerShell.Core) - PowerShell. https://learn.microsoft.com/zh-cn/powershell/module/microsoft.powershell.core/get-module?view=powershell-7.3.
(5) How do I retrieve the available commands from a module?. https://stackoverflow.com/questions/6354317/how-do-i-retrieve-the-available-commands-from-a-module.
(6) Get-Module (Microsoft.PowerShell.Core) - PowerShell. https://learn.microsoft.com/ja-jp/powershell/module/microsoft.powershell.core/get-module?view=powershell-7.4.
(7) How do I retrieve the available commands from a module?. https://stackoverflow.com/questions/6354317/how-do-i-retrieve-the-available-commands-from-a-module.
(8) モジュールについて - PowerShell | Microsoft Learn. https://learn.microsoft.com/ja-jp/powershell/module/microsoft.powershell.core/about/about_modules?view=powershell-7.4.
(9) Get-InstalledModule (PowerShellGet) - PowerShell | Microsoft .... https://learn.microsoft.com/ja-jp/powershell/module/powershellget/get-installedmodule?view=powershellget-2.x.
▼winget listの結果が見切れる
PowerShellウィンドウより、コマンド「winget list」を実行すると、項目の内容が見切れてしまう現象が発生
PS C:\Users\"ユーザー名"> winget list
名前 ID バージョン 利用可能 ソース
-----------------------------------------------------------------------------------------------------------------------
draw.io 22.1.18 JGraph.Draw 22.1.18 23.1.5 winget
ScreenToGif 9N3SQK8PDS8G 2.40.1.0 msstore
Canon Office Printer Utility 9WZDNCRFJ14L 12.7.0.0 msstore
7-Zip 23.01 (x64) 7zip.7zip 23.01 winget
Windows ドライバ パッケージ - Cypress… A55582104F053034007AF6624420AB1CD717B… 08/21/2019 1.2.3.27
Adobe Genuine Service AdobeGenuineService 8.4.0.63
インテル® グラフィックス・コマンド・… 9PLFNLNT3G5G 1.100.5287.0 msstore
Intel® OptaneTM Memory and Storage Ma… 9MZNG5HZWZ1T 18.1.1037.0 msstore
Canon Generic Plus LIPSLX Printer Dri… Canon Generic Plus LIPSLX 7, 6, 0, 0
~ 省略 ~
パイプでFormat-Tableコマンドレットに渡す下記方法をためすもNG
winget list | Format-Table -AutoSize -Wrap
配列やコレクションの表示数を拡張(4 → 100)してもNG
$FormatEnumerationLimit = 100
解決した方法は、単純にPowerShellウィンドウのウィンドウサイズを広げると、
見切れなくなった。
-
見切れ状態
-
見切れ解消
-
stackoverflowでも同じような報告
参考情報:How to sort the output of winget list by column in powershell?