文件在任何操作系统上都处于不断变化的状态。有时它们被创建,有时它们被删除,有时它们被更改,这些都是操作系统要做的正常事情。有时,当文件发生更改时,可能会导致依赖于它的其他应用程序不稳定,例如更改属性文件中的端口号、部署清单中的参数,甚至在不经过源代码管理的情况下修复生产中的代码。
作为管理这些操作系统的一部分,工程师需要一种方法来监视这些关键文件发生的情况,并在出现问题时采取行动。输入 .NET FileSystemWatcher 类和 PowerShell。
在 .NET 和 .NET Core 中,FileSystemWatcher 是位于 System.IO 命名空间中并监视文件的类。在 PowerShell 中,这可能非常有用,尤其是当它与其他 PowerShell 函数结合使用时。
实例化 FileSystemWatcher
通过运行 PowerShell 实例化此类
$watcher = New-Object System.IO.FileSystemWatcher
.完成后,您需要告诉它要监视哪个文件夹。为此,可以将 FileSystemWatcher 对象上的 Path 参数设置为要监视的任何文件夹的路径。如果 Windows 上有一个名为 WatchThisFolder 的文件夹,则可以通过运行
$watcher.Path = 'C:WatchThisFolder'
.
由于此类也在 .NET Core 中,因此可以在 Linux 或 Mac OS 系统上执行所有这些操作,就像在 Windows 系统上一样。例如,如果您在当前用户目录下有一个名为 WatchThisFolder 的 Ubuntu Linux 文件夹,则将运行
$watcher.Path = '/home/ubuntu/WatchThisFolder'
.
本文中的其余代码示例可在任一平台上运行,无需任何更改。
从 FileSystemWatcher 触发事件
现在你有一个新的 FileSystemWatcher 对象,你可以看看引擎盖下并尝试弄清楚它。要查看 FileSystemWatcher 正在监视的特定类型的文件系统事件,请输入
$watcher | Get-Member -MemberType Event
.Get-Member 显示传递到其中的对象包含的所有内容,通过添加 MemberType 筛选器,您可以看到某个类别,在本例中为事件。
这些事件是:
- 改变
- 创建
- 删除
- 处置
- 错误
- 重 命名
当在对象设置为监视的路径上检测到一个或多个这些 FileSystemWatcher 事件时,观察程序对象将引发一个外部事件,您可以为其定义操作。
现在,观察程序对象知道要监视的内容,并且知道它正在监视哪些事件,因此必须将其设置为在检测到操作时引发事件。为此,请运行
$watcher.EnableRaisingEvents = $true
.将此标志视为
$watcher
:如果开关关闭,则如果进行任何更改,则不会发生任何事情。您还可以通过将 IncludeSubdirectories 标志更改为 true,以与执行 EnableRaisingEvents 标志相同的方式告诉它查看嵌套在路径中设置的文件和文件夹。
定义要执行的操作
设置观察程序对象后,必须为其指定一个操作,以便在检测到该更改后执行该操作。这可以像写入系统日志一样简单,也可以像使用源代码的干净拉取来触发实例替换一样激烈。首先,您需要在代码中定义一个操作块。下面是一个写入控制台的:
$action = {
$path = $event.SourceEventArgs.FullPath
$name = $event.SourceEventArgs.Name
$changetype = $event.SourceEventArgs.ChangeType
Write-Host "File $name at path $path was $changetype at $(get-date)"
}
可以看到此代码使用变量从事件中拉取变量,该变量是在观察程序对象创建事件时为您创建的。一旦事件终止,变量也会终止,这意味着它只会包含与该事件相关的数据。$event
使用 Register-ObjectEvent
因此,您已经设置了 FileSystemWatcher,并且您已经拥有了在发生某些事情时要执行的操作。现在,这两个人是分开的,彼此不认识。若要使它们协同工作,必须将操作注册到事件。PowerShell 具有用于此 cmdlet 的整个 cmdlet---Register-ObjectEvent cmdlet。若要使用 Register-ObjectEvent,必须向它传递三项内容:
- FileSystemWatcher 对象
- 要触发操作的事件类型
- 您之前定义的操作
如果您按照上面列出的相同方式设置了所有内容,它将如下所示:“事件操作”可以替换为 FileSystemWatcher 中的任何事件,但这将是一个很好的演示。Register-ObjectEvent $watcher 'Event Action' -Action $action.
测试
现在,您可以对其进行所有测试。在本部分中,你将在指定目录中创建一个新文件,查看事件操作,然后禁用并取消注册该事件。
若要创建新文件并触发事件,请在 PowerShell 中运行以下行。这是在 Ubuntu Linux 上,但如果您在 Windows 上遵循,请将 /home/ubuntu/ 替换为 C: 和 / 替换为 。
New-Item -Path "/home/ubuntu/WatchThisFolder/newFile" -ItemType File
输入该项后,事件将触发并触发操作。
File newFile at path /home/ubuntu/WatchThisFolder/newFile was Created at 09/26/2019 20:49:54
如果启用了 IncludeSubdirectories 标志,则每次在该目录或嵌套在该目录下的任何内容中创建新文件时,它都会触发。现在您知道引发事件有效,请通过运行将其关闭,然后尝试创建一个新文件。应创建文件,但不显示任何事件。如果您正在调试并且不想在文件系统中工作时触发任何内容,这将非常有用。$watcher.EnableRaisingEvents = $false
完成后,运行以从操作中注销事件。现在,即使 EnableRaisingEvents 标志为 true 并且操作发生,操作也不会触发。Get-EventSubscriber | Unregister-Event