You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用PowerShell向HTML文件追加数据实现服务状态前后对比

PowerShell系统健康检查报告追加状态对比实现方案

要实现再次运行脚本时追加新状态列并对比变化,核心思路是判断现有报告是否存在,不存在则生成初始报告,存在则解析并修改现有HTML表格,具体步骤和代码如下:

核心步骤

  • 提前定义报告路径、当前日期等变量,确保存储目录存在
  • 收集本次检查的服务数据,保留唯一标识(服务名称Name)以便后续匹配
  • 检查报告文件:
    • 文件不存在:生成包含初始状态列的HTML报告
    • 文件存在:解析现有HTML的服务表格,添加新状态列,匹配已有服务的状态变化,同时处理新增/删除的服务

完整代码实现

# 基础配置
$computer = $env:COMPUTERNAME
$CurrentDate = Get-Date -Format "yyyy-MM-dd"
$reportDir = "C:\HealthCheck\$computer"
$reportPath = Join-Path $reportDir "Health Report $CurrentDate.html"

# 确保报告目录存在
New-Item -ItemType Directory -Path $reportDir -Force | Out-Null

# 定义HTML样式(替换为你原有的$Style内容)
$Style = @"
<style>
    body { font-family: Arial, sans-serif; margin: 20px; }
    table { border-collapse: collapse; width: 90%; margin: 20px 0; }
    th, td { border: 1px solid #ddd; padding: 8px; text-align: left; }
    th { background-color: #f2f2f2; }
    .changed { background-color: #ffcccc; }
    .new { background-color: #ccffcc; }
</style>
"@

# 收集本次服务检查数据(用Name作为唯一标识,状态列带日期后缀)
$newServiceData = Get-CimInstance Win32_Service -ComputerName $computer | 
    Select-Object DisplayName, Name, StartMode, @{Name="State_$CurrentDate"; Expression={$_.State}} | 
    Sort-Object StartMode, State, DisplayName

# 处理报告生成/追加
if (-not (Test-Path $reportPath)) {
    # 生成初始报告
    $servHead = ConvertTo-Html -As Table -Fragment -PreContent '<H2>Services Information</H2>' | Out-String
    $serviceFragment = $newServiceData | ConvertTo-Html -Fragment
    ConvertTo-Html -Head $Style -PostContent "$servHead $serviceFragment" -Title "System Health Check Report" | 
        Out-File $reportPath -Encoding UTF8
}
else {
    # 读取并解析现有HTML
    $htmlContent = Get-Content $reportPath -Raw -Encoding UTF8
    $htmlDoc = New-Object -ComObject "HTMLFile"
    $htmlDoc.write($htmlContent)

    # 定位服务信息表格(通过前置的H2标题匹配)
    $serviceTable = $null
    foreach ($table in $htmlDoc.getElementsByTagName("table")) {
        $prevElement = $table.previousSibling
        while ($prevElement -and $prevElement.tagName -ne "H2") {
            $prevElement = $prevElement.previousSibling
        }
        if ($prevElement -and $prevElement.innerText -eq "Services Information") {
            $serviceTable = $table
            break
        }
    }

    if ($serviceTable) {
        # 1. 添加新状态列的表头
        $headerRow = $serviceTable.rows[0]
        $newHeader = $htmlDoc.createElement("TH")
        $newHeader.innerText = "新状态($CurrentDate)"
        $headerRow.appendChild($newHeader) | Out-Null

        # 2. 遍历现有表格行,匹配并填充新状态
        $existingServiceNames = @()
        for ($i = 1; $i -lt $serviceTable.rows.length; $i++) {
            $row = $serviceTable.rows[$i]
            $serviceName = $row.cells[1].innerText.Trim()
            $existingServiceNames += $serviceName
            
            $matchingService = $newServiceData | Where-Object { $_.Name -eq $serviceName }
            $newCell = $htmlDoc.createElement("TD")
            
            if ($matchingService) {
                $newCell.innerText = $matchingService."State_$CurrentDate"
                # 状态变化时高亮
                if ($row.cells[$row.cells.length -1].innerText -ne $matchingService."State_$CurrentDate") {
                    $newCell.className = "changed"
                }
            }
            else {
                $newCell.innerText = "服务已删除"
                $newCell.className = "changed"
            }
            $row.appendChild($newCell) | Out-Null
        }

        # 3. 处理本次新增的服务(现有表格中没有的)
        $newServices = $newServiceData | Where-Object { $existingServiceNames -notcontains $_.Name }
        foreach ($service in $newServices) {
            $newRow = $serviceTable.insertRow()
            
            # 填充基础列:DisplayName、Name、StartMode
            $cell = $newRow.insertCell()
            $cell.innerText = $service.DisplayName
            
            $cell = $newRow.insertCell()
            $cell.innerText = $service.Name
            
            $cell = $newRow.insertCell()
            $cell.innerText = $service.StartMode
            
            # 补全历史状态列(标记为"新增服务")
            for ($j = 3; $j -lt $headerRow.cells.length -1; $j++) {
                $cell = $newRow.insertCell()
                $cell.innerText = "新增服务"
            }
            
            # 填充本次状态列并高亮
            $cell = $newRow.insertCell()
            $cell.innerText = $service."State_$CurrentDate"
            $cell.className = "new"
        }

        # 保存修改后的HTML
        $updatedHtml = $htmlDoc.documentElement.outerHTML
        $updatedHtml | Out-File $reportPath -Encoding UTF8
    }
    else {
        Write-Warning "未找到服务信息表格,无法追加数据。"
    }
}

关键细节说明

  • 用Get-CimInstance替代Get-WmiObject:这是PowerShell的现代cmdlet,性能和兼容性更好
  • 服务匹配逻辑:使用Name属性作为唯一标识,比DisplayName更可靠(避免显示名称重复)
  • 状态变化高亮:通过CSS类标记状态变化的单元格(红色背景)和新增服务(绿色背景),直观展示变化
  • 边界处理:覆盖了服务新增、删除、状态变更三种场景,保证报告的完整性

内容的提问来源于stack exchange,提问作者VrindaPrash

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.19 00:49:58