利用阿里雲的API實現動態域名解析
首先在實現動態域名解析之前要具備兩個條件:
第一、你必須有公網 IP,就是你的路由器撥號獲取到的 IP 必須是公網 IP (可以參考 ip138 獲取到的 IP)。長城寬頻沒有公公網 IP 所以就不用往下看了,用內網穿透的工具吧,那天在家搭伺服器時發現聯通給的也是內網IP,果斷投訴他們,讓他們換成公網的 IP。
第二、你必須有阿里雲的域名,API 是阿里雲提供的,阿里雲提供域名解析,所以沒有域名就沒法解析了。
進入正題,先說一下原理:
一個 windows 服務,定時獲取公網 IP ,然後呼叫 API 介面設定解析。
首先從阿里雲上把 SDK 下載下來,原始碼需要自己編譯,這裡我們只用到了 core 和 alidns 兩個專案,一個是核心元件,一個是 dns 介面元件。
其實我只用到了 3 個介面:
- DescribeDomainRecords 獲取域名的解析列表
- AddDomainRecord 新增一條新的解析記錄
- UpdateDomainRecord 修改一條解析記錄
獲取域名的解析列表
CGlobalConfig.AccessKey 是獲取配置檔案裡配置的阿里雲的 AccessKey,這個需要去阿里雲申請(不花錢)。
CGlobalConfig.AccessKeySecret 是獲取配置檔案裡配置的阿里雲的 AccessKeySecret,這個跟 AccessKey 是一對。
domain 變數是域名
IClientProfile clientProfile = DefaultProfile.GetProfile("cn-hangzhou", CGlobalConfig.AccessKey, CGlobalConfig.AccessKeySecret); DefaultAcsClient client = new DefaultAcsClient(clientProfile); DescribeDomainRecordsRequest request = new DescribeDomainRecordsRequest(); request.DomainName = domain; DescribeDomainRecordsResponse response = client.GetAcsResponse(request); List<DescribeDomainRecordsResponse.Record> list = response.DomainRecords;
獲取到的 list 就是這個域名的解析記錄。
DescribeDomainRecordsResponse.Record 物件有以下幾個屬性:
- DomainName 域名
- RecordId 記錄 ID ,唯一標識,是個 GUID
- RR 主機記錄,如果要解析@.exmaple.com,主機記錄要填寫"@”,而不是空
- Type 解析記錄型別,自己去看阿里雲的解析型別,我這裡只用了 A
- Value 解析記錄的值,A 型別的記錄這裡就是 IP 地址了,每次修改的就是這個 Value
獲取到解析記錄後獲取當前的公網 IP 地址,我這裡是從 ip138 上獲取的,沒有時間找介面,就直接解析 HTML 了。
HttpWebRequest request = HttpWebRequest.Create(CGlobalConfig.IPUrl) as HttpWebRequest; using (HttpWebResponse response = request.GetResponse() as HttpWebResponse) { StreamReader reader = new StreamReader(response.GetResponseStream(), Encoding.GetEncoding("GB2312")); string str = reader.ReadToEnd(); reader.Close(); reader.Dispose(); int start = str.IndexOf("["); int end = str.IndexOf("]"); if (start > -1 && end > -1 && end > start) { ip = str.Substring(start + 1, end - start - 1); } }
ip 就是獲取到的 當前公網 IP 地址,然後判斷與當前解析是否一致,不一致時進行解析。
List<DescribeDomainRecordsResponse.Record> list = CDomainHelper.GetDomainRecords(CGlobalConfig.DomainName);
DescribeDomainRecordsResponse.Record record = list.Find(rec => rec.Type == "A" && rec.RR == "dev");
if (record != null)
{
if (record.Value != ip)
{
CLogHelper.WriteInfo("當前 IP:" + ip + " 域名解析 IP:" + record.Value + " 開始修改解析記錄。 ");
record.Value = ip;
CDomainHelper.UpdateDomainRecords(record);
}
else
{
CLogHelper.WriteInfo("當前 IP 與域名解析 IP 相同,不需要修改解析。");
}
}
else
{
CLogHelper.WriteInfo("沒有找到解析需要新增解析記錄。");
record = new DescribeDomainRecordsResponse.Record();
record.RR = "dev";
record.DomainName = CGlobalConfig.DomainName;
record.Type = "A";
record.Value = ip;
CDomainHelper.AddDomainRecords(record);
}
CDomainHelper.AddDomainRecords 是新增解析記錄的方法:
IClientProfile clientProfile = DefaultProfile.GetProfile("cn-hangzhou", CGlobalConfig.AccessKey, CGlobalConfig.AccessKeySecret);
DefaultAcsClient client = new DefaultAcsClient(clientProfile);
AddDomainRecordRequest request = new AddDomainRecordRequest();
request.DomainName = record.DomainName;
request.RR = record.RR;
request.Type = record.Type;
request.Value = record.Value;
AddDomainRecordResponse response = client.GetAcsResponse(request);
CDomainHelper.UpdateDomainRecords 是修改解析記錄的方法:
IClientProfile clientProfile = DefaultProfile.GetProfile("cn-hangzhou", CGlobalConfig.AccessKey, CGlobalConfig.AccessKeySecret);
DefaultAcsClient client = new DefaultAcsClient(clientProfile);
UpdateDomainRecordRequest request = new UpdateDomainRecordRequest();
request.RecordId = record.RecordId;
request.RR = record.RR;
request.Type = record.Type;
request.Value = record.Value;
UpdateDomainRecordResponse response = client.GetAcsResponse(request);
好了,主要的邏輯完成了,然後我們建立一個 window 服務然後在 OnStart 裡啟動一個執行緒,每隔一段時間去解析就可以了。
大家可以下載原始碼進行參考,下載原始碼後需要更改配置檔案:
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<appSettings>
<!-- 阿里雲開發者的 AccessKey -->
<add key="AccessKey" value="阿里雲開發者的AccessKey"/>
<!-- 阿里雲開發者的 AccessKeySecret -->
<add key="AccessKeySecret" value="阿里雲開發者的 AccessKeySecret"/>
<!-- 阿里雲 API 的地址 -->
<add key="APIUrl" value="http://ecs.aliyuncs.com/"/>
<!-- 獲取外網 IP 的地址 -->
<add key="IPUrl" value="http://1212.ip138.com/ic.asp"/>
<!-- 要進行解析的域名 -->
<add key="DomainName" value="要進行解析的域名"/>
</appSettings>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5.2" />
</startup>
</configuration>
需要修改的是 AccessKey,AccessKeySecret,DomainName 這三個配置項。
最後說一下,域名解析不是實時生效的,需要10分鐘的時間。
第一次寫部落格,寫的不好歡迎拍磚。