PowerShell 中的类 Bash 提示符和应用程序运行





0/5 (0投票)
一篇文章,描述了PowerShell脚本和配置文件的技巧,可以让你在PowerShell中获得类似Bash的提示符,并更灵活地运行应用程序。
引言
在批处理脚本中,编写代码来完成简单的事情非常繁琐。PowerShell 让我们更容易地完成这些事情,并且它在访问和控制系统资源方面也表现出色,因为它使用了 .NET Framework。我不得不提到一些我编写过的并且很有用的代码片段。
背景
当我从 Unix/Linux 迁移到 PowerShell 时,我很想念 Bash 提示符。Bash 提示符不会显示整个目录路径,并且有一个家目录符号。这保持了终端的整洁。出于安全原因,PowerShell 施加了许多限制。例如,你有一个脚本 delay.ps1。即使启用了执行策略,你也不能通过输入 delay 来运行它。我决定使用前缀 ss 来运行所有这些程序。现在,有了提供的脚本,我们可以输入 ss scriptname 来简单地运行一个脚本(即使我们省略了扩展名或 .\ 也可以)。
使用代码
将文件 Microsoft.PowerShell_profile.ps1 的代码放入你的配置文件中,并将 ss.ps1 放在你想要存放脚本的位置。
你需要启用你的电脑上的 PowerShell 脚本执行策略。要为当前用户启用它,你可以运行 PS > set-executionpolicy Unrestricted -scope currentuser。
脚本内部
如果想在 Windows PowerShell 中使用类似 Unix 的提示符,我们使用以下代码,其中包含两个函数,prompt
和 get-diralias
。get-diralias
函数在遇到我们设置的家目录时(这里是 E:\Scripts),会返回一个重音符号。
如果不是家目录,那么我们找到一个反斜杠 (\)。仅获取该斜杠后的最后一部分作为子字符串。否则,如果我们发现当前位置字符串以 \ 结尾,我们就知道我们在驱动器的根目录下。在这种情况下,我们只返回驱动器和冒号。
$env:homedir=E:\Scripts
# get the last part of path
function get-diralias ([string]$loc) {
# check if we are in our home script dir
# in that case return grave sign
if ($loc.Equals($env:homedir)) {
return "~"
}
# if it ends with \ that means we are in root of drive
# in that case return drive
$lastindex = [int] $loc.lastindexof("\")
if ($loc.EndsWith("\")) {
return $loc.Remove($lastindex, 1)
}
# Otherwise return only the dir name
$lastindex += 1
$loc = $loc.Substring($lastindex)
return $loc
}
# Set prompt
function prompt {
return "[sa@matrix $(get-diralias($(get-location)))]$ "
}
我们添加了另一个函数 ss
,它提供以下功能
# To go home
$ ss cd
# To edit powershell profile script
$ ss ep
# To open a text/script file with Powershell ISE
$ ss ise filename.ps1
# List programs which are available in app path that can be run
# with simply putting with ss i.e., ss notepad++ or ss chrome
$ ss list-programs
# run a program from apppath, app path in registry
# is a collection of paths when you run a command
# from run dialog box it looks for executable file paths
# there (correct me if I am wrong)
$ ss chrome
Or
$ ss devenv
ss
是一个命令,如果提供的文件路径不存在,它将创建该文件。让我们进入脚本。我们拥有教父函数 ss
,它以适当的方式管理命令行参数,如果没有提供命令行参数则发出警告,并使用这些参数调用 ss.ps1 脚本。我这样做是为了保持配置文件更小。
function ss() {
if ($args.Count -lt 1) {
return "Please provide correct commandline"
}
elseif ($args.Count -eq 1) {
& "$env:homedir\ss.ps1" $args
}
else {
$cmd = $args[0]
# echo "cmd: `"$cmd`""
$cargs = [string]$args
# echo "cargs: `"$cargs`""
$cargs = $cargs.TrimStart($cmd)
$cargs = $cargs.TrimStart()
# echo "cargs: `"$cargs`""
& "$env:homedir\ss.ps1" $args[0] $cargs
}
return ""
}
ss cd
或 ss ep
的功能很容易理解。最初,ss ise
的代码更简单。但是 ise
有时表现不稳定。这就是为什么我将命令行更正为指定绝对文件路径而不是相对路径,即 .\filename.ext 是相对路径,而 e:\folder\filename.ext 是绝对文件路径。
# ss ise: call powershell_ise editor
if ($cmd.ToLower().Equals("ise")) {
$cargs = [string]$args[1]
$cpath = $cargs
# if the file
if ($cargs.IndexOf("\") -eq "-1") {
$cpath =$(get-location).path+"\$cargs"
}
elseif ($cargs.StartsWith("..\")) {
$cpath =$(get-location).path
$cpath =$cpath.Substring(0, $cpath.LastIndexOf("\"))
$cpath +=$cargs.TrimStart("..")
}
elseif ($cargs.StartsWith(".\")) {
$cpath =$(get-location).path+$cargs.TrimStart(".")
}
if (Test-Path $cpath) {
# echo "1. Path: $cpath"
& $env:SystemRoot\system32\WindowsPowerShell\v1.0\powershell_ise.exe $cpath
}
else {
echo "Creating File $cpath as it does not exist."
echo "# Date: $(get-date)"> $cpath
echo "# Author: $env:USERNAME">> $cpath
& $env:SystemRoot\system32\WindowsPowerShell\v1.0\powershell_ise.exe $cpath
}
break
}
要从应用程序路径运行程序,ss
首先会检查以下注册表项是否存在:HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\$(cmdArgument).exe。如果找到它,它将获取该键的默认值,即可执行文件的文件路径。我们删除两端引号。
if (Test-Path "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\$cmd.exe") {
echo "Starting program $origcmd"
$regitem = Get-ItemProperty
"HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\$cmd.exe"
# Get-ItemProperty
"HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\notepad++.exe"
$regcmd = $regitem."(default)"
# Modify the command so that arguments don't get splitted
$regcmd = $regcmd.TrimStart("`"")
$regcmd = $regcmd.TrimEnd("`"")
& "$regcmd" $cargs
break
}
elseif (!(Test-Path "$env:homedir\$cmd.ps1")) {
echo "Please check your command"
break
}
希望这些脚本能帮助你自动化你的工作。谢谢。
历史
- 初始发布 - 2011 年 7 月 11 日。