什么是提供程序

一个PowerShell的提供程序,或者说PSProvider,其本质上是一个适配器。它可以接受某些数据存储,并使得这些介质看起来像是磁盘驱动器一样。
大部分的其他软件程序包都存在提供程序,比如Internet Information Service(IIS)、SQL Server,甚至是活动目录。

可以通过Get-PSProvider命令,查看当前Shell中已经存在的提供程序。

  1. PS C:\> Get-PSProvider
  2. Name Capabilities Drives
  3. ---- ------------ ------
  4. Registry ShouldProcess, Transactions {HKLM, HKCU}
  5. Alias ShouldProcess {Alias}
  6. Environment ShouldProcess {Env}
  7. FileSystem Filter, ShouldProcess, Credentials {C, D, Z}
  8. Function ShouldProcess {Function}
  9. Variable ShouldProcess {Variable}
  10. # 使用环境提供程序,显示操作系统变量%TEMP%。
  11. PS D:\(tmp> Get-Item env:temp
  12. Name Value
  13. ---- -----
  14. TEMP C:\Users\GUORUI~1\AppData\Local\Temp

我们可以通过模块或者管理单元将一些提供程序添加到PowerShell中,这也是PowerShell仅支持的两种扩展方式。有些时候,如果启用了某些PowerShell功能,可能也会新增一个PSProvider。
比如,当开启了远程管理时,会新增一个PSProvider。

  1. # 开启远程管理
  2. PS C:\Windows\system32> Enable-PSRemoting
  3. WinRM 已更新为接收请求。
  4. 成功更改 WinRM 服务类型。
  5. 已启动 WinRM 服务。
  6. PS C:\Windows\system32> Get-PSProvider
  7. Name Capabilities Drives
  8. ---- ------------ ------
  9. Registry ShouldProcess, Transactions {HKLM, HKCU}
  10. Alias ShouldProcess {Alias}
  11. Environment ShouldProcess {Env}
  12. FileSystem Filter, ShouldProcess, Credentials {C, D}
  13. Function ShouldProcess {Function}
  14. Variable ShouldProcess {Variable}
  15. WSMan Credentials {WSMan}

我们可以看出每个提供程序都有各自不同的功能。下面是常见的一些功能描述。

  • **ShouldProcess**:这部分提供程序支持-WhatIf-Confirm参数,保证我们在正式执行这部分脚本之前可以对它们进行测试。
  • **Filter**:在Cmdlet中操作提供程序的数据时,支持-Filter参数。
  • **Credentials**:该提供程序允许使用可变更的凭据连接数据存储。这也就是-Credentials参数的作用。
  • **Transactions**:该提供程序支持事务
    • 也就是允许在该提供程序中,将多个变更作为一个原子操作进行提交或者全部回滚。

      PSDrive

      PSDrive可以通过一个特定的提供程序,连接到某些存储数据的介质。 ```bash PS C:> Get-PSDrive

Name Used (GB) Free (GB) Provider Root


Alias Alias C 112.37 7.63 FileSystem C:\ Cert Certificate \ D 299.66 34.08 FileSystem D:\ Env Environment Function Function HKCU Registry HKEY_CURRENT_USER HKLM Registry HKEY_LOCAL_MACHINE Variable Variable WSMan WSMan Z 355.07 44.93 FileSystem \10.1.2.83\d

  1. 在上面返回的列表中,可以看到有3个驱动器使用了FileSystem提供程序,两个使用了Registry提供程序,等等。
  2. PSProvider会适配对应的数据存储,通过PSDrive机制使得数据存储可被访问,然后可以使用一系列Cmdlets去查阅或者操作每个PSDrive呈现出来的数据。大多数情况下,操作PSDrivecmdlet名词部分都会包含“Item”。<br />![image.png](https://cdn.nlark.com/yuque/0/2022/png/635565/1653472582474-999951ba-92a1-489f-9a49-62cfb687679a.png#clientId=u1ef435a4-c76d-4&crop=0&crop=0&crop=1&crop=1&from=paste&height=586&id=u0eb45ab3&margin=%5Bobject%20Object%5D&name=image.png&originHeight=645&originWidth=1675&originalType=binary&ratio=1&rotation=0&showTitle=false&size=1219531&status=done&style=none&taskId=u5ccf893d-bb86-436b-8d2a-b77dd442840&title=&width=1522.7272397230486)
  3. <a name="n19E6"></a>
  4. ## FileSystem的结构
  5. Windows文件系统(以及macOSLinux的文件系统)主要由3种对象组成:磁盘驱动器、文件夹和文件。磁盘驱动器是最上层的对象,包含文件夹和文件。文件夹是一种容器对象,它可以包含文件以及其他文件夹。<br />PowerShell中的术语和文件系统中的略有不同。PowerShell并不会使用“文件”以及“文件夹”的说法。
  6. - PSDrive可能不是指向某个文件系统,比如PSDrive可以映射到注册表。
  7. - PowerShell采用更通俗的说法:“项”(Item)。一个文件或者一个文件夹都叫作项。
  8. 每个项基本上都会存在对应的属性。比如,一个文件项可能有最后写入的时间、是否只读等属性。一些项,比如文件夹,可能包含子项(子项包含在文件夹项中)。
  9. - ClearCopyGetMoveNewRemoveRename以及Set等动词可以应用于这些项(比如文件或者文件夹)以及它们对应的属性(比如该项最后写入的时间或者该项是否只读)。
  10. - Item名词对应的是单独对象,比如文件或者文件夹。
  11. - ItemProperty代表一个项对应的属性。比如只读、项创建时间、长度等。
  12. - ChildItem名词对应一个项(比如文件或者子文件夹)包含于另外一个项(文件夹)中。
  13. 某些Cmdlet在某些特定场合下不一定能正常工作。
  14. - 比如,**FileSystem提供程序不支持事务**,所以文件系统驱动器下的Cmdlet中的命令都不支持-UseTransaction参数。
  15. - 再比如,**注册表不支持Filter功能**,所以注册表驱动器下的Cmdlet也都不支持-Filter参数。
  16. 某些PSProvider并不具有对应的项属性。比如,Environment这个PSProvider主要用来构造PowerShell中可用的ENV:类型驱动器(如Env:\PSModulePath)。该驱动器主要的作用是访问Windows中的环境变量,但是如下所示,它并没有对应的项属性。<br />![image.png](https://cdn.nlark.com/yuque/0/2022/png/635565/1653473021206-1cd19e56-ed47-4d85-ae8f-984e259d8638.png#clientId=u1ef435a4-c76d-4&crop=0&crop=0&crop=1&crop=1&from=paste&height=244&id=ue62a1c69&margin=%5Bobject%20Object%5D&name=image.png&originHeight=268&originWidth=1556&originalType=binary&ratio=1&rotation=0&showTitle=false&size=400223&status=done&style=none&taskId=u5a9b284a-2cfe-4833-9756-f15de241fd3&title=&width=1414.5454238860082)<br />通过以上可知,即便Cmdlet知道如何实现某些功能,也并不意味着该提供程序真正支持对应的操作。
  17. <a name="oRf4r"></a>
  18. ## 使用文件系统
  19. 在使用提供程序时,需要熟悉的另外一个CmdletSet-Location(别名cd)。该参数的功能是将Shell中当前路径,变更为不同路径。比如变更到另一个文件夹下:<br />![image.png](https://cdn.nlark.com/yuque/0/2022/png/635565/1653473254916-55e56594-ad57-4822-a7af-ef8d3d02d828.png#clientId=u1ef435a4-c76d-4&crop=0&crop=0&crop=1&crop=1&from=paste&height=67&id=uc0037528&margin=%5Bobject%20Object%5D&name=image.png&originHeight=83&originWidth=425&originalType=binary&ratio=1&rotation=0&showTitle=false&size=7081&status=done&style=none&taskId=u724b527d-ac61-4d12-a760-ccaee2e803f&title=&width=341.3636169433594)
  20. <a name="yEpHq"></a>
  21. ### New-Item
  22. New-Item这个Cmdlet在很多地方都是通用的,它可以用来新建文件夹、文件、注册表项以及其他项,所以你必须告知你希望创建的类型是什么。
  23. ```powershell
  24. # 创建一个目录
  25. New-Item -Path "d:\" -Name "logfiles" -ItemType "directory"
  26. # 在当前目录创建一个文件
  27. New-Item -Path . -Name "testfile1.txt" -ItemType "file" -Value "This is a text string."
  28. # 创建多个文件
  29. New-Item -ItemType "file" -Path "c:\ps-test\test.txt", "c:\ps-test\Logs\test.log"

PowerShell中也包含MKDir命令。很多人都认为该命令是New-Item的别名,但使用MKDir并不需要输入类型。
内部实现上,Mkdir是一个函数,而并不是一个别名。但是实际上,它仍然调用了New-Item,只不过隐式赋予了-Type Directory这个参数。

通配符与路径

大部分项的Cmdlet都包含了-Path属性。默认情况下,该属性支持通配符输入。

Get-ChildItem

比如,我们查看Get-ChildItem(别名Dir)的完整帮助文档:
image.png
通配符:

  • “*”:代表0个或者多个字符;
  • “? ”:仅代表单个字符。

拓展:Get-ChildItem的-Filter、-Include和-Exclude参数之间有什么不同?

  • 如果查询一个容器,Include与Exclude必须使用 –Recurse参数。
  • Filter使用了PS提供程序的过滤功能,并不是所有的提供程序都支持该参数。

    • 例如,你可以在文件系统中使用DIR –filter,但无法在注册表中使用。
    • 在注册表中,可以使用DIR –include命令实现过滤输出结果。 ```powershell PS C:\Users\guoruilong> Get-ChildItem -Path HKLM:\HARDWARE -Include E

      Hive: HKEY_LOCAL_MACHINE\HARDWARE

Name Property


DESCRIPTION DEVICEMAP UEFI RESOURCEMAP

  1. <a name="KydWn"></a>
  2. ### 参数LiteralPath
  3. 在文件或者文件夹的名称中,不允许带有“*”或者“? ”字符。但在注册表中,你可以看到一些项的名称中包含“? ”字符。这将导致一个问题:当在一个路径中使用了“*”或者“? ”,PowerShell会如何对待,是作为一个通配符还是一个特定的字符?<br />针对此问题,PowerShell给出的解决办法是新增一个参数`-LiteralPath`。该参数并不支持通配符。<br />![image.png](https://cdn.nlark.com/yuque/0/2022/png/635565/1653475189180-85e97a33-a753-487d-8af7-0091d26a5c51.png#clientId=u80b6ebdc-480f-4&crop=0&crop=0&crop=1&crop=1&from=paste&height=249&id=u6324a1c2&margin=%5Bobject%20Object%5D&name=image.png&originHeight=303&originWidth=692&originalType=binary&ratio=1&rotation=0&showTitle=false&size=57410&status=done&style=none&taskId=ue5c16820-77d8-419d-8d42-6ce74be64cd&title=&width=569.0880737304688)<br />如果需要查询名字中带有*或者?,就要使用-LiteralPath参数,而不要使用-Path。需要注意的是,-LiteralPath这个参数不可隐式赋予,否则,将默认使用-Path参数。
  4. <a name="dUnZi"></a>
  5. ## 使用其他提供程序 - 注册表
  6. 如果想对其他提供程序有个大致的认识,以及了解其他项的Cmdlet如何工作,最好的办法就是去尝试一下非文件系统格式的PSDrive。在PowerShell内置的提供程序中,注册表应该算是比较好的一个示例。
  7. ```powershell
  8. PS C:\> Set-Location -Path HKCU: # 切换到HKEY_CURRENT_USER
  9. PS HKCU:\> Set-Location -Path SOFTWARE
  10. PS HKCU:\SOFTWARE> Get-ChildItem
  11. PS HKCU:\> cd .\SOFTWARE\Microsoft\Windows\
  12. PS HKCU:\SOFTWARE\Microsoft\Windows\> dir
  13. Hive: HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows
  14. Name Property
  15. ---- --------
  16. AssignedAccessConfiguration
  17. CurrentVersion
  18. DWM Composition : 1
  19. ColorizationColor : 3288365271
  20. ColorizationColorBalance : 89
  21. ColorizationAfterglow : 3288365271
  22. ColorizationAfterglowBalance : 10
  23. ColorizationBlurBalance : 1
  24. EnableWindowColorization : 0
  25. ColorizationGlassAttribute : 1
  26. AccentColor : 4292311040
  27. ColorPrevalence : 0
  28. EnableAeroPeek : 1
  29. AlwaysHibernateThumbnails : 0

在该列表中可以看到EnableWindowColorization的键值,现在将它修改为1。

  1. # 可以使用-Name参数,代替-PSProperty参数。
  2. PS HKCU:\SOFTWARE\Microsoft\Windows\> Set-ItemProperty -Path dwm -PSProperty EnableWindowColorization 1
  3. PS HKCU:\SOFTWARE\Microsoft\Windows\> dir
  4. Hive: HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows
  5. Name Property
  6. ---- --------
  7. AssignedAccessConfiguration
  8. CurrentVersion
  9. DWM Composition : 1
  10. ColorizationColor : 3288365271
  11. ColorizationColorBalance : 89
  12. ColorizationAfterglow : 3288365271
  13. ColorizationAfterglowBalance : 10
  14. ColorizationBlurBalance : 1
  15. EnableWindowColorization : 1
  16. ColorizationGlassAttribute : 1
  17. AccentColor : 4292311040
  18. ColorPrevalence : 0
  19. EnableAeroPeek : 1
  20. AlwaysHibernateThumbnails : 0

采用这种方法,可以处理其他提供程序类似的问题。