最近在做爬蟲的作業,今天學習的內容是關於DNS解析模塊的制作的。使用的庫為ARSoft.Tools.Net,它是一個非常強大的開源DNS控件庫,包含.Net SPF validation, SenderID validation以及DNS Client、DNS Server接口。使用該接口可輕松實現DNS客戶請求端及服務器解析端。項目地址:http://arsofttoolsnet.codeplex.com/,Nuget包地址:https://www.nuget.org/packages/ARSoft.Tools.Net/。
首先引入Nuget包:
Install-Package ARSoft.Tools.Net
下面開始具體實現:
/// <summary> /// DNS解析 /// </summary> /// <param name="dnsServer">DNS服務器IP</param> /// <param name="timeOut">解析超時時間</param> /// <param name="url">解析網址</param> /// <param name="isSuccess">是否解析成功</param> /// <returns>解析到的IP信息</returns> public static IPAddress DnsResolver(string dnsServer, int timeOut, string url, out bool isSuccess) { //初始化DnsClient,第一個參數為DNS服務器的IP,第二個參數為超時時間 var dnsClient = new DnsClient(IPAddress.Parse(dnsServer), timeOut); //解析域名。將域名請求發送至DNS服務器解析,第一個參數為需要解析的域名,第二個參數為 //解析類型, RecordType.A為IPV4類型 //DnsMessage dnsMessage = dnsClient.Resolve("www.sina.com", RecordType.A); var s = new Stopwatch(); s.Start(); var dnsMessage = dnsClient.Resolve(DomainName.Parse(url)); s.Stop(); Console.WriteLine(s.Elapsed.Milliseconds); //若返回結果為空,或者存在錯誤,則該請求失敗。 if (dnsMessage == null || (dnsMessage.ReturnCode != ReturnCode.NoError && dnsMessage.ReturnCode != ReturnCode.NxDomain)) { isSuccess= false; } //循環遍歷返回結果,將返回的IPV4記錄添加到結果集List中。 if (dnsMessage != null) foreach (var dnsRecord in dnsMessage.AnswerRecords) { var aRecord = dnsRecord as ARecord; if (aRecord == null) continue; isSuccess = true; return aRecord.Address; } isSuccess= false; return null; }
調用方法:
bool isSuccess; IPAddress ip = DnsResolver("223.5.5.5", 200, "shaoweicloud.cn", out isSuccess); if (isSuccess) Console.WriteLine(ip);
懂的使用方法後我們可以對它做進一步封裝,得到DnsResolver類:
using System; using System.Collections.Generic; using System.Diagnostics; using System.Net; using ARSoft.Tools.Net; using ARSoft.Tools.Net.Dns; namespace Crawler.Protocol { public class DnsResolver { public TimeSpan TimeSpan { get; set; } public string Url { get; set; } public List Record { get; set; } public string DnsServer { get; set; } public int TimeOut { get; set; } public ReturnCode ReturnCode { get; set; } public bool IsSuccess { get; private set; } public DnsResolver(string url, string dnsServer = "223.5.5.5", int timeOut = 200) { Url = url; DnsServer = dnsServer; TimeOut = timeOut; Record=new List(); Dig(); } public void Dig() { //初始化DnsClient,第一個參數為DNS服務器的IP,第二個參數為超時時間 var dnsClient = new DnsClient(IPAddress.Parse(DnsServer), TimeOut); var s = new Stopwatch(); s.Start(); //解析域名。將域名請求發送至DNS服務器解析,參數為需要解析的域名 var dnsMessage = dnsClient.Resolve(DomainName.Parse(Url)); s.Stop(); TimeSpan = s.Elapsed; //若返回結果為空,或者存在錯誤,則該請求失敗。 if (dnsMessage == null || (dnsMessage.ReturnCode != ReturnCode.NoError && dnsMessage.ReturnCode != ReturnCode.NxDomain)) IsSuccess = false; //循環遍歷返回結果,將返回的IPV4記錄添加到結果集List中。 if (dnsMessage != null) foreach (var dnsRecord in dnsMessage.AnswerRecords) { var aRecord = dnsRecord as ARecord; if (aRecord == null) continue; IsSuccess = true; Record.Add(aRecord); } if (dnsMessage != null) ReturnCode = dnsMessage.ReturnCode; } } }
調用方法:
DnsResolver dns = new DnsResolver("shaoweicloud.cn"); if (dns.IsSuccess) Console.WriteLine(dns.Record[0]);
至此,DNS解析模塊就基本結束了,至於為什麼標題中標注了半成品,是因為我想在基本的DNS解析功能的基礎上根據解析到DNS信息中的TTL做一套信息緩存機制,減少不必要的重復查詢,目前還在考慮使用何種方法,後續實現會更新。