[玩转系统] PowerShell 脚本:如何在重构中幸存
作者:精品下载站 日期:2024-12-14 13:03:05 浏览:13 分类:玩电脑
PowerShell 脚本:如何在重构中幸存
如果您曾经继承过一个脚本或一组 PowerShell 脚本,您可能知道这种挫败感。你有一种经过多年经验磨练出来的特定编码方式,你会遇到……让我们说是怪物。
你继承了你所见过的最丑陋、最可怕的撒旦 PowerShell 脚本。我是说这些脚本打破了书中的每一条规则。
不要被吓跑!一切都可以解决;甚至是自以为无所不知的新手编写的意大利面条脚本。
留在我身边。
构建 Pester 测试来验证环境变化
如果您读过 The Pester Book,您可能知道,您可以在各个“层”中构建测试。
- 单元测试测试代码执行(考虑将哪些参数传递给函数、代码在 if/then 构造中遵循的分支等)。
- 集成测试测试代码所做的更改。例如,测试
Set-Content
是否将适当的字符串添加到文件中,或者New-Item
添加了预期的注册表项。如果脚本打开防火墙帖子,Get-NetFirewallRule
是否返回预期输出? - 测试最终目标的验收测试。如果您的脚本打开防火墙端口,您将尝试使用 Test-NetConnection 连接到该端口并验证服务是否正在运行。验收测试确认最终目标。
由于您最终将彻底更改代码,因此请跳过单元测试。同样,此时,您实际上并没有测试混乱代码是否执行了它应该执行的操作(原作者应该这样做)。
您需要构建一组广泛的集成测试来确认此代码所做的所有更改。您需要为每个注册表项或它更改的值、它移动的文件、它安装的更新等等一切构建测试!
为什么只进行集成测试?因为您必须确保一旦开始对原始代码库进行大量更改,您就有一个可以按下的按钮来确保您已获得所有内容。如果没有集成测试,您可以重构整个代码库,忘记 20 件不同的事情,您的代码不会产生错误,然后继续。
几个月后,您将遇到一个模糊的边缘情况,后来发现,您只是忘记在重构的代码中添加该异常。
将乱七八糟的东西收集到一处
就像近藤麻理惠所说,你首先需要把所有乱七八糟的东西收集起来,并把它们放到一个地方。整洁的 PowerShell 脚本总是给我带来快乐!如果混乱的内容被分成跨不同文件和文件夹的脚本,每个文件和文件夹都互相引用,请删除所有这些“链接”
将所有内容放入单个 PowerShell 脚本中。通过首先组合所有代码,您将能够更轻松地查找/替换字符串,而不必遵循脚本执行的兔子踪迹,并且您的理智将始终避免切换选项卡。
如果您遇到了由 10 个脚本调用其他调用模块函数的脚本组成的混乱情况,请将所有内容合并到一个 PS1 脚本中。在此阶段,您不关心保持可行的解决方案。只需将所有内容转储到一个脚本中即可。
使用区域
保留脚本中原始代码来源的某种历史记录的一种好方法是使用区域。让您创建代码“桶”。然后,您可以参考代码的来源来命名每个区域。
例如:
#region bad_script1.ps1
## Contents of bad_script1.ps1 here
#endregion
#region bad_script2.ps1
## Contents of bad_script2.ps1 here
#endregion
删除依赖项
接下来,继续尽可能地简化混乱脚本。为此,您需要删除尽可能多的依赖项。依赖关系包括代码中的参数、变量以及引用的任何文件、数据库等。
删除变量和参数
为 PowerShell 脚本中声明的所有变量赋值,或者完全删除它们。如果您正在使用可能包含数百个变量的脚本,则需要简化故障排除。您需要使其尽可能容易地遵循代码。变量和其他引用在成品中非常有用,但此时您需要简化代码。
删除所有参数,但一定要记录它们。您可能需要在最终产品中重新引入这些参数。
例如,如果您必须将许多 PowerShell 脚本合并在一起,那么您可能会有类似于以下代码片段的行:
#region bad script1
param(
[Parameter()]
[string]$Param1
)
$variable =
## code here
#endregion
#region bad script2
param(
[Parameter()]
[string]$Param2
)
## code here
#endregion
删除所有参数块,并为这些变量分配一个静态值,如下所示。
[string]$ServerName = 'MYSWEETSNOWFLAKE'
## code here
#endregion
[string]$IpAddress = '192.168.0.1'
## code here
#endregion
拉近任何外部依赖关系
您无法删除所有依赖项,但请务必尽可能简化它们。例如,如果该脚本引用不同服务器上的各种文件,请将它们放入脚本所在的同一文件夹中。
如果 PowerShell 脚本正在查询数据库,请尝试运行本地副本。同样,删除依赖项的目的是简化您必须遵循的代码。
您的单一综合混乱脚本绝对不应该有任何参数,或者依赖于任何其他外部系统来运行。要测试它,您应该能够不带参数运行.\messscript.ps1,并且它应该由单一用例运行。
将所有日志记录/调试信息变成注释
简化混乱脚本的下一步是删除所有日志记录或调试代码。您可能会看到很多 Write-Host
、Write-Verbose
,甚至可能是自定义的 Write-Log
函数。要么注释掉它,要么完全删除它们。
您可以完全删除日志记录和调试行,但我建议将它们注释掉。您可能需要此信息来了解代码在某些时候正在做什么。一旦您熟悉了代码流程,您就可以删除注释。
日志记录和调试行对脚本的功能没有任何贡献。相反,他们使事情变得复杂,并且需要更长的时间来破译。
构建测试环境并使所有测试失败
无论原始解决方案对一堆虚拟机 (VM)、云资源还是其他任何内容进行更改,您都需要一个干净的测试环境。
构建一个测试环境,其中包含与正在发生的混乱情况不同的所有配置项。您需要一个包含与正在发生的混乱变化相反的一切的环境,以便您可以在事后进行比较。
构建测试环境后,运行集成测试套件。所有测试都失败了吗?完美的!您现在知道您的环境没有应用混乱代码应该更改的配置。
重要提示:不要忘记确保所有集成测试在您的测试环境中都失败。这个很重要!如果没有,一个配置项可能已经被应用,你将无法知道它是一开始就是这样还是你的重构代码更新了它。
您现在已经设置了一个原始环境来比较更改。
让混乱再次运转
现在,您应该将所有 PowerShell 脚本和模块捆绑到一个(可能有数千行)PS1 脚本中,并且一组集成测试均已通过。怎么办?
现在是时候开始修复变量引用、参数值、命令引用和其他阻止该解决方案在单个 PS1 脚本中工作的逻辑了。
不要试图立即开始完善这个解决方案。只需尝试让您的综合代码大杂烩完全像以前一样工作,尽管是通过单个脚本实现的。
您在此阶段的目标是让单个脚本的行为就像它被分成 1,000 个片段时一样。你需要一个统一的混乱起点。
继续进行更改并运行测试套件,直到所有测试通过。
困难的部分:重构 PowerShell 脚本
现在是时候开始重构代码了。这是有趣的部分!根据您的混乱脚本正在做什么,很大程度上取决于您的重构方式,但在下面您会找到一些建议。
为各种任务构建结构
每个大型脚本都有其内部执行的各种“任务”。也许是获取 NIC 属性、构建虚拟机、创建邮箱、删除用户等等。脚本完成任务。现在,这些任务可能都合并在一起了。
创建一个新脚本并将这些任务拆分为单个 PowerShell 脚本或另一个干净脚本中的区域。
更好地分解这些任务将帮助您了解代码的进展,同时在代码重构方面取得一些进展。
构建配置数据
此时,您在一个 PS1 脚本中就拥有了一切。这不好。您需要开始稍微模块化该脚本。对于您的第一个任务,构建一个配置数据存储。什么是配置数据存储?它是存储可能随时间变化的配置项的通用术语。
这部分是您之前记录的那些参数发挥作用的地方。
也许您有一个脚本,可以从 Windows 部署一直到配置操作系统来配置新服务器。在之前的mess脚本中,您发现了各种参数,例如ComputerName
、IpAddress
、RunPatching
等。这些参数改变了mess脚本的行为。您可能想保留它们。
在此阶段不必重新引入这些参数,而是创建一个配置数据存储来存储所有这些参数。例如,您可以在脚本所在的同一文件夹中创建一个名为 configuration.psd1 的文件。
configuration.psd1 文件可能如下所示:
@{
'DefaultServerConfig' = @{
'ServerName' = 'SRV1'
'ComputerNamePrefix' = 'xxxx'
'IpAddress' = $null
'RunPatching' = $true
}
}
然后,在混乱脚本内部,您可以添加一个名为 Get-Configuration
的函数,该函数读取配置并将其分配给变量。
function Get-Configuration {
param()
Import-PowerShellDataFile -Path "$PSScriptRoot\configuration.psd1"
}
$configuration = Get-Configuration
现在,将其他脚本中的所有参数引用替换为对解决方案配置的引用,如下所示。
$Param1 = $configuration.ServerName
## code here
#endregion
$Param2 = $configuration.IpAddress
## code here
#endregion
您不必使用 PowerShell 数据文件。您可以使用 JSON、YAML 或 XML(如果您喜欢痛苦的话)。
您现在正在从逻辑代码中分离出配置。
消除裁员
议程上的下一个项目是裁员。冗余可以通过多种方式渗透到代码中。最常见的方法之一是忽略使用循环。
例如,如果您看到一些如下所示的行:
Do-Thing -ComputerName XXX -Thing yyyy
Do-Thing -ComputerName rrr -Thing hhhh
无需调用命令两次,而是使用参数展开和 foreach 循环来简化它。
$paramSets = @(
@{
ComputerName = 'XXX'
Thing = 'yyyy'
}
@{
ComputerName = 'rrr'
Thing = 'hhhh'
}
}
foreach ($set in $paramSets) {
Do-Thing @set
}
上面的代码片段只是一个单一场景。有无数种方法可以删除冗余代码。添加循环可能是减少代码长度和简化事情的最简单方法之一。
模块化!
将庞大的混乱脚本分成小块,所有小块一起工作并构建一组标准的模块或功能,它们都可以共享。
- 创建一个或多个 PowerShell 模块并将脚本转换为使用其中的函数。
- 为所有任务创建小型、单一用途的函数。
你如何知道你什么时候完成
你怎么知道你什么时候完成了?如果您对所有这些问题的回答都是“是”,那么您就完成了。拍拍自己的背。
- 您对新的解决方案满意吗?
- 您是否遵循了本文中的所有提示?
- 在新的测试环境中运行旧解决方案和新解决方案后,您之前构建的所有集成测试是否都通过了?
如果您对所有这些问题的回答都是“是”,那么恭喜您,您已经完成了!
猜你还喜欢
- 03-30 [玩转系统] 如何用批处理实现关机,注销,重启和锁定计算机
- 02-14 [系统故障] Win10下报错:该文件没有与之关联的应用来执行该操作
- 01-07 [系统问题] Win10--解决锁屏后会断网的问题
- 01-02 [系统技巧] Windows系统如何关闭防火墙保姆式教程,超详细
- 12-15 [玩转系统] 如何在 Windows 10 和 11 上允许多个 RDP 会话
- 12-15 [玩转系统] 查找 Exchange/Microsoft 365 中不活动(未使用)的通讯组列表
- 12-15 [玩转系统] 如何在 Windows 上安装远程服务器管理工具 (RSAT)
- 12-15 [玩转系统] 如何在 Windows 上重置组策略设置
- 12-15 [玩转系统] 如何获取计算机上的本地管理员列表?
- 12-15 [玩转系统] 在 Visual Studio Code 中连接到 MS SQL Server 数据库
- 12-15 [玩转系统] 如何降级 Windows Server 版本或许可证
- 12-15 [玩转系统] 如何允许非管理员用户在 Windows 中启动/停止服务
取消回复欢迎 你 发表评论:
- 精品推荐!
-
- 最新文章
- 热门文章
- 热评文章
[短剧] 2025年06月03日 精选+付费短剧推荐25部
[软件合集] 25年6月3日 精选软件44个
[短剧合集] 2025年06月2日 精选+付费短剧推荐39部
[软件合集] 25年6月2日 精选软件18个
[软件合集] 25年6月1日 精选软件15个
[短剧合集] 2025年06月1日 精选+付费短剧推荐59部
[短剧] 2025年05月31日 精选+付费短剧推荐58部
[软件合集] 25年5月31日 精选软件66个
[电影] 黄沙漫天(2025) 4K.EDRMAX.杜比全景声 / 4K杜比视界/杜比全景声
[风口福利] 短视频红利新风口!炬焰创作者平台重磅激励来袭
[剧集] [央视][笑傲江湖][2001][DVD-RMVB][高清][40集全]李亚鹏、许晴、苗乙乙
[电视剧] 欢乐颂.5部全 (2016-2024)
[电视剧] [突围] [45集全] [WEB-MP4/每集1.5GB] [国语/内嵌中文字幕] [4K-2160P] [无水印]
[影视] 【稀有资源】香港老片 艺坛照妖镜之96应召名册 (1996)
[剧集] 神经风云(2023)(完结).4K
[剧集] [BT] [TVB] [黑夜彩虹(2003)] [全21集] [粤语中字] [TV-RMVB]
[资源] B站充电视频合集,包含多位重量级up主,全是大佬真金白银买来的~【99GB】
[影视] 内地绝版高清录像带 [mpg]
[书籍] 古今奇书禁书三教九流资料大合集 猎奇必备珍藏资源PDF版 1.14G
[美图] 2W美女个美女小姐姐,饱眼福
[电视剧] [突围] [45集全] [WEB-MP4/每集1.5GB] [国语/内嵌中文字幕] [4K-2160P] [无水印]
[剧集] [央视][笑傲江湖][2001][DVD-RMVB][高清][40集全]李亚鹏、许晴、苗乙乙
[电影] 美国队长4 4K原盘REMUX 杜比视界 内封简繁英双语字幕 49G
[电影] 死神来了(1-6)大合集!
[软件合集] 25年05月13日 精选软件16个
[精品软件] 25年05月15日 精选软件18个
[绝版资源] 南与北 第1-2季 合集 North and South (1985) /美国/豆瓣: 8.8[1080P][中文字幕]
[软件] 25年05月14日 精选软件57个
[短剧] 2025年05月14日 精选+付费短剧推荐39部
[短剧] 2025年05月15日 精选+付费短剧推荐36部
- 最新评论
-
- 热门tag