2011-12-23 9 views
1

PowerShellプロジェクトをモジュールに分割しました。しかし、彼らはモジュールなので、私はそれらを変更するたびにリロードする必要があります。だから、私はFileSystemWatcherを持っているループを書いて、.psm1ファイルの1つが変更された場合、そのモジュールをリロードするか、インポートします。他の作業環境に影響を与えるために、開いている作業環境からモジュールを再ロードする方法

問題は、上記のループが私の作業環境で他のスクリプトを実行させないため、新しい環境に同じモジュールがロード/リロードされないということです。私は、これらのモジュールをPowerShellの主要なデフォルトのフォルダから外しておく必要があります。同じ環境でモジュールが変更されたり特定の環境に影響を与えた場合にモジュールをリロードするスクリプトを実行する方法はありますか?


UPDATE

だから私は、次のモジュール-Loader.ps1スクリプトを実行します。 'FileChanged'イベントに関連付けられたコードブロックは、変更後に* .psm1ファイルを保存すると起動します。しかし、2つの問題が発生します: 1)保存すると2回発生します

2a)モジュールがロードされていない場合、Import-Module $ PWD \ ModuleNameが実行されますが、少なくとも実際にロードされません(ロードする環境で同じコードを実行した場合)

2b)ロードされていて、モジュールを削除しようとすると、エラーが存在しません。

# create a FileSystemWatcher on the currect directory 
$filter = '*.psm1' 
$folder = $PWD 
$watcher = New-object IO.FileSystemWatcher $folder, $filter -Property @{IncludeSubdirectories = $false; EnableRaisingEvents = $true; NotifyFilter = [IO.NotifyFilters]'LastWrite'} 
Register-ObjectEvent $watcher Changed -SourceIdentifier FileChanged -Action { 
$name = $Event.SourceEventArgs.Name 
$filename = $name.Remove($name.IndexOf('.'), 5) 

$loadedModule = Get-Module | ? { $_.Name -eq $filename } 
write-host $filename 

if ($loadedModule) { 
    write-host "Reloading Module $folder\$($filename)" 
    Reload-Module $folder\$filename 
} else { 
    write-host "Importing Module $folder\$($filename)" 
    Import-Module $folder\$filename 
} 
} 

私は、このセッションで実行されているが、イベント内のコード・ブロックは、この特定の環境に関連付けられていないと考えています。

+0

私はあなたの質問を理解していません。ループなので、他のコードが実行されないようにしていますか?もしそうなら、ループを使用する代わりにイベントハンドラを登録することによって、ファイルシステム監視プログラムを非同期的にスクリプトブロックから起動させることができます。もしそれがあなたの必要なもののように聞こえたら、私はそれのいくつかの例のコードを与えることができます。 –

+0

@Andy:はい、ループ内にあるため、他のコードをブロックしています。モジュールの読み込み/読み込みはファイルシステムウォッチャーが実行されている現在の環境にのみ行われるため、読み込み/読み込みされたモジュールに依存するスクリプトを再実行することはできません。私はイベントが消えるのを待っているのかどうか確信が持てません。何が起こっているのかをハードコードする必要があるからです。しかし、それほど多くない場合は、いくつかの例を投稿できますか? – pghtech

答えて

2

ここでは、何かが変更されたときにフォルダを共有フォルダにコピーするコードの例を示します。それはちょっと

:-)私の小さなDropboxの実装の任意の時間などChangedなどのファイルシステム監視イベントタイプのいずれかが発生し、Register-ObjectEventコマンドレットの-Actionパラメータで指定されたコードが発生します。

-Actionコードでは、-Forceパラメータを使用してImport-Moduleと呼び出し、現在のデータを メモリに上書きします。

function Backup-Folder { 
    & robocopy.exe "c:\folder" "\\server\share" /MIR /W:10 /R:10 
} 

$watcher = New-Object System.IO.FileSystemWatcher 
$watcher.Path = "c:\folder" 
$watcher.IncludeSubdirectories = $true 
$watcher.EnableRaisingEvents = $true 

Register-ObjectEvent $watcher "Changed" -Action { Backup-Folder } 
Register-ObjectEvent $watcher "Created" -Action { Backup-Folder } 
Register-ObjectEvent $watcher "Deleted" -Action { Backup-Folder } 
Register-ObjectEvent $watcher "Renamed" -Action { Backup-Folder } 
+0

私はあなたの提案を受けて、この同じルートに行きました、そして、私のアクションは基本的に、モジュールが読み込まれ、変更されたモジュール(.psm1)ファイルをインポートまたはリロードするかどうかをチェックします。しかし、コードブロックの実行時に返されるものは何でも、モジュールはロードされません。少なくとも、コードブロックをイベントにバインドするスクリプトが実行された環境では、 – pghtech

+0

コードブロックに環境固有の情報を渡し、特定のセッション/環境に対してモジュールをロードする方法があるかどうかを確認しようとしていました。 – pghtech

+0

私はあなたの言うことを正しく理解しています。 1. Import-Moduleは初期モジュールをロードします。 2.モジュールファイルが変更されます。 3.イベントハンドラがスクリプトブロックを起動します。 4.スクリプトブロックがモジュールを再ロードします。 5.モジュールの変更は有効になりません。そうですか? –

関連する問題