PowerShell 技能连载 - 如何查找包含指定参数的命令

Get-Command 是当您需要查找某个命令来完成一件事情时的主要工具。

您可以这样搜索动词和/或名词:

# find all cmdlets/functions that stop things
Get-Command -Verb Stop
# find all cmdlets/functions that affect services
Get-Command -Noun Service

从 PowerShell 3.0 开始,Get-Command 还可以根据一个给定的参数查找 cmdlet 或函数:

# new in PS3 and better
# find all cmdlets/functions with a -ComputerName parameter
Get-Command -ParameterName ComputerName

请注意 Get-Command 是在已加载的 cmdlet/函数中搜索。请确保在搜索前已导入了所需的模块。

PowerShell 技能连载 - 获取 CPU 核心和处理器信息

通过一行 WMI 代码,就可以查看您的 CPU 详情:

PS> Get-WmiObject -Class Win32_Processor | Select-Object -Property Name, Number*

Name                                    NumberOfCores NumberOfLogicalProcessors
----                                    ------------- -------------------------
Intel(R) Core(TM) i7-26...                          2                         4

PowerShell 技能连载 - 安装 Windows 功能

在服务器中,Powershell 可以通过 Install-WindowsFeature 命令安装 Windows 功能。

若您将 Install-WindowsFeature 返回的结果保存下来,则可以用 Get-WindowsFeature 查看安装的状态:

# install features on server and save result in $result
Install-WindowsFeature -Name AD-Domain-Services, DNS -IncludeManagementTools -OutVariable result -Verbose

# view the result of your change
Get-WindowsFeature -Name $result.FeatureResult.Name

PowerShell 技能连载 - 创建动态脚本块

脚本块是一段可执行的 PowerShell 代码。您通常可以将语句包裹在大括号中创建脚本块。

若要在脚本中动态创建脚本块,以下是将一个字符串转换为脚本块的方法。

$scriptblock = [ScriptBlock]::Create('notepad')

通过这种方法,您的代码首先以字符串的形式创建代码,然后将字符串转换为脚本块,然后将脚本块传递给您需要的 cmdlet(例如 Invoke-Command):

PS> Invoke-Command -ScriptBlock 'notepad'
Cannot convert  the "notepad" value of type "System.String" to type
"System.Management.Automation.ScriptBlock". (raised by:  Invoke-Command)

PS> Invoke-Command -ScriptBlock ([ScriptBlock]::Create('notepad'))

PowerShell 技能连载 - 管理 NTFS 权限继承

缺省情况下,文件和文件夹从它们的父节点继承权限。要停用继承,并且只保留显式权限,请做以下两件事情:增加你需要显式权限,然后禁止继承。

这个示例代码创建了一个名为“_PermissionNoInheritance_”的文件夹,然后为当前用户赋予读权限,为管理员组赋予完整权限,并且禁止继承。

# create folder
$Path = 'c:\PermissionNoInheritance'
$null = New-Item -Path $Path -ItemType Directory -ErrorAction SilentlyContinue

# get current permissions
$acl = Get-Acl -Path $path

# add a new permission for current user
$permission = $env:username, 'Read,Modify', 'ContainerInherit, ObjectInherit', 'None', 'Allow'
$rule = New-Object -TypeName System.Security.AccessControl.FileSystemAccessRule -ArgumentList $permission
$acl.SetAccessRule($rule)

# add a new permission for Administrators
$permission = 'Administrators', 'FullControl', 'ContainerInherit, ObjectInherit', 'None', 'Allow'
$rule = New-Object -TypeName System.Security.AccessControl.FileSystemAccessRule -ArgumentList $permission
$acl.SetAccessRule($rule)

# disable inheritance
$acl.SetAccessRuleProtection($true, $false)

# set new permissions
$acl | Set-Acl -Path $path

PowerShell 技能连载 - 移除非继承的 NTFS 权限

在前一个例子中,我们演示了如何向已有的文件夹添加新的 NTFS 权限。如果您希望重置权限并且移除所有之前所有非继承的 NTFS 权限,以下是示例代码:

# make sure this folder exists
$Path = 'c:\sampleFolderNTFS'

# get explicit permissions
$acl = Get-Acl -Path $path
$acl.Access |
  Where-Object { $_.isInherited -eq $false } |
  # ...and remove them
  ForEach-Object { $acl.RemoveAccessRuleAll($_) }

# set new permissions
$acl | Set-Acl -Path $path

PowerShell 技能连载 - 获取非继承的 NTFS 权限

要查看某个文件或者文件夹被直接赋予了哪些 NTFS 权限,请注意“isInherited”属性。这段代码将创建一个名为“_sampleFolderNTFS_”的新文件夹,并且列出所有非继承的 NTFS 权限。当您创建该文件夹时,它只拥有继承的权限,所以您查看非继承权限的时候获得不到任何结果:

$Path = 'c:\sampleFolderNTFS'

# create new folder
$null = New-Item -Path $Path -ItemType Directory -ErrorAction SilentlyContinue

# get permissions
$acl = Get-Acl -Path $path
$acl.Access |
  Where-Object { $_.isInherited -eq $false }

当您增加了非继承权限时,这段代码将会产生结果。这是通过 PowerShell 增加非继承权限的方法。它将针对当前用户添加读、写、修改权限:

$acl = Get-Acl -Path $path

# add a new permission
$permission = $env:username, 'Read,Write,Modify', 'ContainerInherit, ObjectInherit', 'None', 'Allow'
$rule = New-Object -TypeName System.Security.AccessControl.FileSystemAccessRule -ArgumentList $permission
$acl.SetAccessRule($rule)

# set new permissions
$acl | Set-Acl -Path $path

PowerShell 技能连载 - 管理 NTFS 权限

在前一个技能中我们演示了如何向一个文件夹增加 NTFS 权限。要查看可以设置哪些权限,看以下示例:

PS> [System.Enum]::GetNames([System.Security.AccessControl.FileSystemRights])
ListDirectory
ReadData
WriteData
CreateFiles
CreateDirectories
AppendData
ReadExtendedAttributes
WriteExtendedAttributes
Traverse
ExecuteFile
DeleteSubdirectoriesAndFiles
ReadAttributes
WriteAttributes
Write
Delete
ReadPermissions
Read
ReadAndExecute
Modify
ChangePermissions
TakeOwnership
Synchronize
FullControl

假设您已创建了一个名为“_protectedfolder_”的文件夹:

$Path = 'c:\protectedFolder'

# create new folder
$null = New-Item -Path $Path -ItemType Directory

要为“_Tobias_”用户(请将用户名替换为您系统中实际存在的用户名)增加文件系统权限,请运行这段代码:

# get permissions
$acl = Get-Acl -Path $path

# add a new permission
$permission = 'Tobias', 'Read,Write,Modify', 'ContainerInherit, ObjectInherit', 'None', 'Allow'
$rule = New-Object -TypeName System.Security.AccessControl.FileSystemAccessRule -ArgumentList $permission
$acl.SetAccessRule($rule)

# set new permissions
$acl | Set-Acl -Path $path

PowerShell 技能连载 - 创建一个包含 NTFS 权限的文件夹

您常常会需要创建一个文件夹并且为它设置 NTFS 权限。

这是一个简单的创建新文件夹并演示如何向已有权限中增加新的权限的示例代码:

$Path = 'c:\protectedFolder'

# create new folder
$null = New-Item -Path $Path -ItemType Directory

# get permissions
$acl = Get-Acl -Path $path

# add a new permission
$permission = 'Everyone', 'FullControl', 'ContainerInherit, ObjectInherit', 'None', 'Allow'
$rule = New-Object -TypeName System.Security.AccessControl.FileSystemAccessRule -ArgumentList $permission
$acl.SetAccessRule($rule)

# add another new permission
# WARNING: Replace username "Tobias" with the user name or group that you want to grant permissions
$permission = 'Tobias', 'FullControl', 'ContainerInherit, ObjectInherit', 'None', 'Allow'
$rule = New-Object -TypeName System.Security.AccessControl.FileSystemAccessRule -ArgumentList $permission
$acl.SetAccessRule($rule)

# set new permissions
$acl | Set-Acl -Path $path

PowerShell 技能连载 - 分割超长代码行

为了提高可读性,您可以将超长的 PowerShell 代码行拆分成多行。

Get-Service | Where-Object { $_.Status -eq 'Running' }

Get-Service |
  Where-Object { $_.Status -eq 'Running' }

在管道符之后,您可以加入一个换行。您也可以安全地在一个左大括号之后、右大括号之前加入一个换行:

Get-Service |
  Where-Object {
    $_.Status -eq 'Running'
  }

如果您需要在其它地方换行,那么请在换行之前加入一个反引号:

Get-Service |
Where-Object `
{
  $_.Status -eq 'Running'
}