Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/ssh/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 广告搜索、属性和口述用法_C#_Dictionary_Active Directory - Fatal编程技术网

C# 广告搜索、属性和口述用法

C# 广告搜索、属性和口述用法,c#,dictionary,active-directory,C#,Dictionary,Active Directory,为了确定计算机帐户是否为孤立帐户,我想查询所有受信任域的所有域控制器,以检索所有计算机的lastLogon和lastLogonTimeStamp。我有一个程序,至少在我的测试环境中可以运行,但我有几个问题,希望您能够回答 我使用的方法是查找域和域控制器,然后检索AD信息,使用尽可能少的资源网络/域控制器CPU和RAM吗?如何改进 字典键/值对中是否可能有多个值? 有一本LastLogIn字典和另一本LastLogInTimestamp字典似乎是浪费 参考字典和广告属性:如何检查不存在的值,而不是

为了确定计算机帐户是否为孤立帐户,我想查询所有受信任域的所有域控制器,以检索所有计算机的lastLogon和lastLogonTimeStamp。我有一个程序,至少在我的测试环境中可以运行,但我有几个问题,希望您能够回答

我使用的方法是查找域和域控制器,然后检索AD信息,使用尽可能少的资源网络/域控制器CPU和RAM吗?如何改进

字典键/值对中是否可能有多个值? 有一本LastLogIn字典和另一本LastLogInTimestamp字典似乎是浪费

参考字典和广告属性:如何检查不存在的值,而不是使用Try/Catch

试一试 {//这个直流电流比上一个直流电流大吗? 如果dict_LastLogIn[pc] 下面是整个代码:

using System;
using System.Collections.Generic;
using System.DirectoryServices;
using System.DirectoryServices.ActiveDirectory;


namespace dictionary
{
    class Program
    {
        internal static Dictionary<string, long> dict_LastLogIn =
            new Dictionary<string, long>();
        internal static Dictionary<string, long> dict_LastLogInTimeStamp =
            new Dictionary<string, long>();
        internal static Dictionary<string, DateTime> output =
            new Dictionary<string, DateTime>();

        internal static bool AreAllDCsResponding = true;

        static void Main(string[] args)
        {
            Console.BufferWidth = 150;
            Console.BufferHeight = 9999;
            Console.WindowWidth = 150;

            Dictionary<String, int> dict_domainList = new Dictionary<String, int>();
            Dictionary<String, int> dict_dcList = new Dictionary<String, int>();

            //Get the current domain's trusts.
            Domain currentDomain = Domain.GetCurrentDomain();
            Console.WriteLine("Retrieved the current Domain as {0}", currentDomain.ToString());
            var domainTrusts = currentDomain.GetAllTrustRelationships();
            Console.WriteLine("  {0} trusts were found.", domainTrusts.Count);
            //Add the current domain to the dictonary.  It won't be in domainTrusts!
            dict_domainList.Add(currentDomain.ToString(), 0);
            // Then add the other domains to the dictonary...
            foreach (TrustRelationshipInformation trust in domainTrusts)
            {
                dict_domainList.Add(trust.TargetName.Substring(0, trust.TargetName.IndexOf(".")).ToUpper(), 0);
                Console.WriteLine("    Adding {0} to the list of trusts.", trust.TargetName.Substring(0, trust.TargetName.IndexOf(".")).ToUpper());
            }
            // Now get all DCs per domain
            foreach (var pair in dict_domainList)
            {
                DirectoryContext dc = new DirectoryContext(DirectoryContextType.Domain, pair.Key);
                Domain _Domain = Domain.GetDomain(dc);
                foreach (DomainController Server in _Domain.DomainControllers)
                {
                    dict_dcList.Add(Server.Name, 0);
                    Console.WriteLine("      Adding {0} to the list of DCs.", Server.Name.ToUpper());

                }
                // Now search through every DC
                foreach (var _pair in dict_dcList)
                {
                    Console.WriteLine("        Querying {0} for Computer objects.", _pair.Key.ToUpper());
                    Search(pair.Key);
                    Console.WriteLine("\n");
                    Console.WriteLine("The following Computer objects were found:");
                }

                if (AreAllDCsResponding == true)
                {
                    ConvertTimeStamp(dict_LastLogIn);
                }
                else
                {
                    ConvertTimeStamp(dict_LastLogInTimeStamp);
                }
                Console.ReadLine();
            }
        }

        internal static void Search(string domainName)
        {
            DirectoryEntry entry = new DirectoryEntry("LDAP://" + domainName);
            DirectorySearcher mySearcher = new DirectorySearcher(entry);
            mySearcher.Filter = ("(&(ObjectCategory=computer))");//(lastlogon=*)(lastlogonTimeStamp=*))");
            mySearcher.SizeLimit = int.MaxValue;
            mySearcher.PropertiesToLoad.Add("DistinguishedName");
            mySearcher.PropertiesToLoad.Add("lastlogon");
            mySearcher.PropertiesToLoad.Add("lastlogonTimeStamp");
            try
            {
                foreach (System.DirectoryServices.SearchResult result in mySearcher.FindAll())
                {
                    string pc = result.Properties["DistinguishedName"][0].ToString();
                    try
                    {   // Is this DC more current than the last?
                        if (dict_LastLogIn[pc] < (long)result.Properties["lastlogon"][0])
                        {
                            dict_LastLogIn[pc] = (long)result.Properties["lastlogon"][0];
                        }
                    }
                    catch
                    {   // The item doesn't exist yet..
                        try
                        {
                            dict_LastLogIn[pc] = (long)result.Properties["lastlogon"][0];
                        }
                        catch
                        {   // .. or
                            // There is no last LastLogin...
                            dict_LastLogIn[pc] = 0;
                        }
                    }

                    try
                    {
                        // Not yet replicated?...
                        if (dict_LastLogInTimeStamp[pc] < (long)result.Properties["lastlogonTimeStamp"][0])
                        {
                            dict_LastLogInTimeStamp[pc] = (long)result.Properties["lastlogonTimeStamp"][0];
                        }
                    }
                    catch
                    {   // The item doesn't exist yet..
                        try
                        {
                            dict_LastLogInTimeStamp[pc] = (long)result.Properties["lastlogonTimeStamp"][0];
                        }
                        catch
                        {   // .. or
                            // There is no last LastLoginTimeStamp...
                            dict_LastLogInTimeStamp[pc] = 0;
                        }
                    }
                }
            }
            catch (System.Runtime.InteropServices.COMException)
            {
                //If even one DC doesn't answer, don't use LastLogon!  
                //Use the less accurate, but replicated(!) LastLogonTimeStamp. 
                AreAllDCsResponding = false;
            }
        }

        internal static void ConvertTimeStamp(Dictionary<string, long> _dict)
        {
            foreach (var pair in _dict)
            {
                output.Add(pair.Key, DateTime.FromFileTime(pair.Value));
                Console.WriteLine("{0} - {1}", pair.Key, DateTime.FromFileTime(pair.Value));
            }
        }
    }
}

谢谢你能提供的任何帮助

从高层次上讲,我不确定您的最终目的是什么,但是,您确定要查询每个DC的lastLogon吗?这可能真的很贵。还有,你为什么要走信任链?您确定不只是想要给定林中的所有域。域吗

回答你的问题:

从性能上看,这看起来不错,但是您应该做几件事:

将过滤器调整为&objectCategory=computerobjectClass=computer 添加mySearcher.PageSize=1000 删除mySearcher.SizeLimit=int.MaxValue 你可以用元组-。或者只需将自定义类定义为您的值,然后将Dictionary声明为您的Dictionary:

公共类LogonTimeStamps {

公共长LastLogon{get;set;}

公共长LastLogonItemStamp{get;set;}

}

对于字典,请使用myDictionary.containskeyourkey。对于AD,您应该能够使用result.Properties.ContainsyourAttribute


布莱恩,谢谢你的意见结局?当然,总是有更多的…我需要我们多个林中所有域的信息,因此信任。首先,它将用最新的“上次AD连接时间”更新数据库。未连接到网络(例如1年)的计算机将被禁用。至于1,你的过滤器当然更好。为什么要减小页面大小?有好处吗?每个查询将收到大约10000个结果,因此MaxSize不能保持默认值1000.2。使用字典,我可以直接基于可分辨名称访问该对,而无需循环。元组或自定义类可以这样做吗?怎样对不起,我不是一个程序员,只是一个管理员,希望扩展我的工具集…3。我得调查一下我还认为,在对每个DC进行预处理之前,我会对它们进行ping处理,这将为每个无法访问的DC节省最多两分钟的时间。除非有人修改,否则AD的最大默认页面大小为1000。只要您设置此选项,DirectorySearcher就会自动分页记录。SizeLimit参数不是必需的。至于字典,您将存储字典,因此仍然可以通过DN访问它。最后,对于perf,您可能还需要查看多线程,以便在单个线程中查询每个DC。使用ThreadPool类可以很容易地做到这一点。如果不设置MaxSize,我只能得到1000个结果。也许有些东西被修改了。多线程听起来很棒,但是如果两个或多个线程在字典中同时尝试更改同一个键/值对,会发生什么情况呢?假设我想要线程Searchpair.Key;这是如何实现的?在我看来,多线程实际上是一个完全独立的问题。在较高的层次上,您可以使用lock关键字来处理并发性。我不知道为什么SizeLimit会在这里播放-医生说它在>1000时被忽略。页面大小是这里最重要的一个。