C# - 通过远程注册表获取上次Windows更新 - OpenSubKey(“WindowsUpdate”)返回NULL

时间:2015-11-10 17:53:17

标签: c# registry

尝试从远程计算机上读取上一次成功的Windows Update时间,但是在密钥上出现错误

  

HKLM \ SOFTWARE \微软\的Windows \ CurrentVersion \ WindowsUpdate的\

示例代码:

var hive = RegistryKey.OpenRemoteBaseKey(RegistryHive.LocalMachine, machineName);
var soft = hive.OpenSubKey("SOFTWARE");
var micro = soft.OpenSubKey("Microsoft");
var wind = micro.OpenSubKey("Windows");
var currver = wind.OpenSubKey("CurrentVersion");
var wu = currver.OpenSubKey("WindowsUpdate"); // returns NULL
var au = wu.OpenSubKey("Auto Update"); // throws exception "Object referece not set to an instance of an object"
var res = au.OpenSubKey("Results");
var inst = res.OpenSubKey("Install");
var lastUpdate = inst.GetValue("LastSuccessTime").ToString();
Console.WriteLine(lastUpdate);

我已经确认密钥是正确的,我不确定问题是什么。

enter image description here

修改 我收到的错误是

  

对象引用未设置为对象的实例。

因为子项“WindowsUpdate”返回NULL。

1 个答案:

答案 0 :(得分:1)

我从OpenSubKey()方法获取NULL的原因是因为我需要将RegistryView参数添加到OpenRemoteBaseKey(RegistryHive.LocalMachine, machineName, RegistryView.Default|64|32);

感谢Alex K和this StackOverflow Answer的评论,我能够通过使用以下静态方法替换我的代码来解决我的问题。只需添加对 WUApiLib.dll 的引用,然后添加

using WUApiLib;
public static IEnumerable<IUpdateHistoryEntry> GetAllUpdates(string machineName)
{
    try
    {
        Type t = Type.GetTypeFromProgID("Microsoft.Update.Session", machineName);
        UpdateSession session = (UpdateSession)Activator.CreateInstance(t);
        IUpdateSearcher updateSearcher = session.CreateUpdateSearcher();
        int count = updateSearcher.GetTotalHistoryCount();
        IUpdateHistoryEntryCollection history = updateSearcher.QueryHistory(0, count);
        return history.Cast<IUpdateHistoryEntry>();
    }
    catch (Exception ex)
    {
        throw ex;
    }
}
public static DateTime GetLastSuccessfulUpdateTime(string machineName)
{
    DateTime lastUpdate = DateTime.Parse("0001-01-01 00:00:01");
    try
    {
        var updates = GetAllUpdates(machineName);
        if (updates.Where(u => u.HResult == 0).Count() > 0)
        {
            lastUpdate = updates.Where(u => u.HResult == 0).OrderBy(x => x.Date).Last().Date;
        }
    }
    catch (Exception ex)
    {
        throw ex;
    }
    return lastUpdate;
}

使用,

DateTime lastSuccessfulUpdate = GetLastSuccessfulUpdateTime("PC-01");

注意:作为参考,这仅返回单个最近成功的更新包的时间戳。 表示所有其他Windows更新都已成功。要获取失败更新的列表,请使用以下命令:

IList<IUpdateHistoryEntry> failedUpdates = GetAllUpdates("PC01")
.Where(upd => upd.HResult != 0).ToList();

获取失败更新的所有时间戳,

IList<DateTime> failedUpdates = GetAllUpdates("PC01")
.Where(upd => upd.HResult != 0)
.Select(upd => upd.Date).ToList();