楚狐在线 - 资讯杂烩
资讯杂烩   在线工具   益智游戏   影音娱乐   网站导航

腾讯云域名云解析服务(DNS)API接口PHP封装


  目前互联网上提供免费的域名托管服务的厂家很多,如阿里云/万网、腾讯云、CloudFlare、华为云等等,我们将域名托管到这些云解析DNS服务商后,虽然服务商都提供了控制台用于域名及解析记录的管理,但是有时候如果我们需要自己实现DDNS动态域名解析等一些基于官网API接口能力的功能,就需要使用到官网提供的API能力,本文将针对腾讯云的API接口,通过PHP封装了常用的函数类,用于托管域名、记录集等的管理。
  本文旨在帮助开发者快速使用集成腾讯云域名云解析服务(DNS)的API接口,实现对域名(Zone)和解析记录(Record Set)的自动化管理,如域名托管、记录添加及修改等。
  阿里云API官方文档地址详见:https://cloud.tencent.com/document/api/1427
  下面是PHP实现的API封装类,代码如下:

/**
 * 基于腾讯云API 3.0接口 
 * 调用方法示例:
 * DNSPodDomainDNS::Obj()->DescribeRecordList('example.com');
 * 参考文档
 * 域名API文档:https://cloud.tencent.com/document/api/242
 * 云解析API文档 :https://cloud.tencent.com/document/api/1427
 * 引用或者使用本文,请注明来源:楚狐在线- https://chuhu.org
**/
class DNSPodDomainDNS
{
	#下面为子账号apisdkuser的密钥
	# 在https://console.cloud.tencent.com/cam 用户列表里面 建立子账号 设置密钥
	private $secretId = "AK********************************";
	private $secretKey = "******************************";
	private static $obj  = null;

	public static function Obj ()
	{
		if(is_null(self::$obj))
		{
			self::$obj = new self();
		}
		return self::$obj;
	}

	//***********************以下为域名管理服务***********************//
	//获取我在腾讯云注册的域名列表
	public function DescribeDomainNameList()
	{
		$param1 = array('Limit'=>100); 
		$val =  $this->requestDomain($param1, 'DescribeDomainNameList');
		return $val;
		//echo printJsonToHTML($val);
	}

	//获取域名基本信息(含域名DNS服务器)
	public function DescribeDomainBaseInfo($Domain)
	{
		$param1 = array('Domain'=>$Domain); 
		$val =  $this->requestDomain($param1, 'DescribeDomainBaseInfo');
		return $val;
		//echo printJsonToHTML($val);
	}

	//域名注册查询
	//Period 年限。该参数为空时无法查询溢价词域名,如 '1',则显示溢价域名和溢价的价格
	public function CheckDomain($Domain, $Period=null)
	{
		$param1 = array('DomainName'=>$Domain);
		if(!empty($Period)) {
			$param1['Period']=$Period;
		};
		$val =  $this->requestDomain($param1, 'CheckDomain');
		return $val;
		//echo printJsonToHTML($val);
	}

	//批量域名 DNS 修改
	//$domainName = ['example.net'];
	//$domainNameServer = array('aaaaa.ns.cloudflare.com','bbbbb.ns.cloudflare.com'); 
	public function ModifyDomainDNSBatch($Domains, $Dns)
	{
		$param1 = array('Domains'=>$Domains, 'Dns'=>$Dns); 
		$val =  $this->requestDomain($param1, 'ModifyDomainDNSBatch');
		return $val;
		//echo printJsonToHTML($val);
	}


	//批量操作日志状态
	//LogIds.N	是	Array of Integer  [111]
	public function CheckBatchStatus($LogIds)
	{
		$param1 = array('LogIds'=>$LogIds); 
		$val =  $this->requestDomain($param1, 'CheckBatchStatus');
		return $val;
		//echo printJsonToHTML($val);
	}

	//********************************************************************************//
	//********************************************************************************//
	//********************************************************************************//
	//***********************以上为域名管理、以下为域名DNS解析服务***********************//
	//********************************************************************************//
	//********************************************************************************//
	//********************************************************************************//

	//获取域名列表
	public function DescribeDomainList()
	{
		$param1 = array('Type'=>'ALL');  
		$val =  $this->requestDNSPod($param1, 'DescribeDomainList');
		return $val;
	}

	//增加域名解析记录:增加单域名记录值
	public function CreateRecord($Domain, $RR, $recordType, $value)
	{
		$param1 = array('Domain'=>$Domain,'SubDomain'=>$RR,'RecordLine'=>'默认','RecordType'=>$recordType,'Value'=>$value,'TTL'=>600);  
		$val =  $this->requestDNSPod($param1,'CreateRecord');
		return $val;
	}

	//增加域名解析记录:增加单域名记录值
	public function CreateRecord2($Domain, $RR, $recordType, $value)
	{
		$param1 = array('Domain'=>$Domain,'SubDomain'=>$RR,'RecordLine'=>'默认','RecordType'=>$recordType,'Value'=>$value,'TTL'=>600); 
		$val =  $this->requestDNSPod($param1,'CreateRecord');
		return $val;
	}

	//更新域名解析记录:修改单域名记录值,实现DDNS
	public function ModifyRecord($Domain, $recordId, $RR, $recordType, $value)
	{
		$param1 = array('Domain'=>$Domain,'SubDomain'=>$RR,'RecordId'=>$recordId,'RecordLine'=>'默认','RecordType'=>$recordType,'Value'=>$value);  
		$val =  $this->requestDNSPod($param1,'ModifyRecord');
		return $val;
	}

	//删除域名解析记录:删除单域名记录值,目前只能一个记录一个记录的删除。
	public function DeleteRecord($Domain, $recordId)
	{
		$param1 = array('Domain'=>$Domain,'RecordId'=>$recordId);  
		$val =  $this->requestDNSPod($param1,'DeleteRecord');
		return $val;
	}

	//获取域名的解析记录列表:获取当前域名的所有解析记录
	public function DescribeRecordList($Domain)
	{
		$param1 = array('Domain'=>$Domain);  
		$val =  $this->requestDNSPod($param1,'DescribeRecordList');
		return $val;
	}

	//获取记录信息:根据ID获取某个记录的解析值
	public function DescribeRecord($Domain, $RecordId)
	{
		$param1 = array('Domain'=>$Domain,'RecordId'=>$RecordId);  
		$val =  $this->requestDNSPod($param1,'DescribeRecord');
		return $val;
	}

	//获取记录信息:根据Subdomain获取某个记录的解析值
	//若不指定$RecordType,传入参数null
	public function DescribeRecordBySubdomain($Domain, $Subdomain, $RecordType)
	{
		if($RecordType==null || $RecordType=="") {
			$param1 = array('Domain'=>$Domain,'Subdomain'=>$Subdomain);
		} else {
			$param1 = array('Domain'=>$Domain,'Subdomain'=>$Subdomain,'RecordType'=>$RecordType);
		}
		$val =  $this->requestDNSPod($param1,'DescribeRecordList');
		return $val;
	}

	//DDNS更新处理,若域名记录不存在,则直接创建 (DDNS主用)
	//$Domain 主域名
	//$Domain  耳机域名名称,不需要完整的。
	//主要用于DDNS的更新
	//与UpdateDNSRecord传入参数一样,增加了记录值是否存在的判断。
	public function ModifyDynamicDNS($RR,$Domain, $value, $type="A")
	{
		//查出主域名下记录,看是否子域名的解析记录。
		$data = $this->DescribeRecordList2($Domain);
		$data = json_decode($data,true);
		$data = array_filter($data['Response']['RecordList'], function($item) use ($RR, $type) {
				return $item['Name'] === $RR && $item['Type'] === $type;
		});
		$data = array_values($data); //重构数组,删除空
		$rc = count($data);
		if($rc==0)
		{
			//没有记录, 创建按记录。
			$rtn = $this->CreateRecord2($Domain, $RR, $type, $value);
			$rtn = json_decode($rtn,true);
			if(count(array_column($rtn,'Error'))==1){
				echo "域名".$RR.".".$Domain."的".$type."记录不存在,创建失败。";
			}else {
				echo "域名".$RR.".".$Domain."创建成功,并配置".$type."记录为:".$value;
			}
		}
		else if($rc>1)
		{
			echo "域名".$RR.".".$Domain."的".$type."记录有".$rc."条,更新记录失败!";
		} else {
			if($data[0]['Value']==$value){
				echo "处理完成:".$RR.".".$Domain."当前".$data[0]['Type']."记录【".$data[0]['Value']."】与新值【".$value."】一致,无需修改。";
			} else {
				$param1 = array('Domain'=>$Domain,'SubDomain'=>$RR,'RecordId'=>$data[0]['RecordId'],'RecordLine'=>'默认','Value'=>$value);
				$val =  $this->requestDNSPod($param1,'ModifyDynamicDNS');
				$val = json_decode($val,true);
				if(count(array_column($val,'Error'))==1)
				{
					echo "处理失败:".$val['Response']['Error']['Message'];
				}
				else
				{
					if($RR=="@")
					{
						echo "处理完成:".$Domain."的".$type."记录【".$data[0]['Value']."】已修改为【".$value."】。";
					}
					else
					{
						echo "处理完成:".$RR.".".$Domain."的".$type."记录【".$data[0]['Value']."】已修改为【".$value."】。";
					}
				}
			}
		}
	}

	//更新动态 DNS 记录:
	public function ModifyDynamicDNS2($Domain, $recordId, $RR, $value)
	{
		$param1 = array('Domain'=>$Domain,'SubDomain'=>$RR,'RecordId'=>$recordId,'RecordLine'=>'默认','Value'=>$value);  
		$val =  $this->requestDNSPod($param1,'ModifyDynamicDNS');
		return $val;
	}

	//删除单个域名下的所有解析记录
	function DeleteRecordList($Domain)
	{
		//查询源域名记录
		$data = $this->DescribeRecordList2($Domain);
		$data = json_decode($data,true);
		//print_r($data);
		if(count(array_column($data,'Error'))==1)
		{
			echo "域名【".$Domain."】当前主机记录列表为空,无需删除!";
			return;
		}
		$ListCount = $data['Response']['RecordCountInfo']['ListCount'];
		echo "下面将删除域名【".$Domain."】的".$ListCount."条记录:
\n";
		foreach($data['Response']['RecordList'] as $v)
		{
			$rtn = $this->DeleteRecord2($Domain, $v['RecordId']);
			$rtn = json_decode($rtn,true);
			if(count(array_column($rtn,'Error'))==1) 
			{
				echo "域名 ".$Domain." 的主机 ".$v['Name']." 的 ".$v['Type']." 记录[ ".$v['Value']." ]删除失败:".$rtn['Response']['Error']['Message']."(Code:".$rtn['Response']['Error']['Code'].")
\n";
			}
			else
			{
				echo "域名 ".$Domain." 的主机 ".$v['Name']." 的 ".$v['Type']." 记录[ ".$v['Value']." ]删除成功(RecordId=".$v['RecordId'].")。
\n";
			}
		}	
	}
	//***********************以上为域名DNS解析服务***********************//

	//构建腾讯云 域名注册 API 3.0 版本请求方法
	private function requestDomain($param,$action)
	{
		$timestamp = time();
		$region = "ap-chengdu";
		$version = "2018-08-08";
		$algorithm = "TC3-HMAC-SHA256";
		$service = "domain";

		//$host = "domain.tencentcloudapi.com"; //就近地域接入(推荐,只支持非金融区)
		$host = "domain.ap-chengdu.tencentcloudapi.com"; //西南地区(成都)

		// step 1: build canonical request string
		$httpRequestMethod = "POST";
		$canonicalUri = "/";
		$canonicalQueryString = "";
		$canonicalHeaders = "content-type:application/json\n"."host:".$host."\n";
		$signedHeaders = "content-type;host";
		$payload = json_encode($param);	//php5.6以上才要加第二个参数
		$hashedRequestPayload = hash("SHA256", $payload);
		$canonicalRequest = $httpRequestMethod."\n"
			.$canonicalUri."\n"
			.$canonicalQueryString."\n"
			.$canonicalHeaders."\n"
			.$signedHeaders."\n"
			.$hashedRequestPayload;
		// echo $canonicalRequest.PHP_EOL;

		// step 2: build string to sign
		$date = gmdate("Y-m-d", $timestamp);
		$credentialScope = $date."/".$service."/tc3_request";
		$hashedCanonicalRequest = hash("SHA256", $canonicalRequest);
		$stringToSign = $algorithm."\n"
			.$timestamp."\n"
			.$credentialScope."\n"
			.$hashedCanonicalRequest;
		// echo $stringToSign.PHP_EOL;

		// step 3: sign string
		$secretDate = hash_hmac("SHA256", $date, "TC3".$this->secretKey, true);
		$secretService = hash_hmac("SHA256", $service, $secretDate, true);
		$secretSigning = hash_hmac("SHA256", "tc3_request", $secretService, true);
		$signature = hash_hmac("SHA256", $stringToSign, $secretSigning);
		// echo $signature.PHP_EOL;

		// step 4: build authorization
		$authorization = $algorithm
			." Credential=".$this->secretId."/".$credentialScope
			.", SignedHeaders=content-type;host, Signature=".$signature;
		// echo $authorization.PHP_EOL;

		$url = "https://".$host;
		$header[] = "Authorization:".$authorization;
		$header[] = "Content-Type:application/json";
		$header[] = "Host:".$host;
		$header[] = "X-TC-Action:".$action;
		$header[] = "X-TC-Timestamp:".$timestamp;
		$header[] = "X-TC-Version:".$version;
		$header[] = "X-TC-Region:".$region;
		$header[] = "X-TC-Language:zh-CN";
		$res = $this->CurlRequest($url,'post',$payload,$header);
		return $res;
	}

	//构建腾讯云 DNSPod API 3.0 版本请求方法
	private function requestDNSPod($param,$action)
	{
		$timestamp = time();
		$region = "ap-chengdu";
		$version = "2021-03-23";
		$algorithm = "TC3-HMAC-SHA256";
		$service = "dnspod";

		//$host = "dnspod.tencentcloudapi.com"; //就近地域接入(推荐,只支持非金融区)
		$host = "dnspod.ap-chengdu.tencentcloudapi.com"; //西南地区(成都)

		// step 1: build canonical request string
		$httpRequestMethod = "POST";
		$canonicalUri = "/";
		$canonicalQueryString = "";
		$canonicalHeaders = "content-type:application/json\n"."host:".$host."\n";
		$signedHeaders = "content-type;host";
		$payload = json_encode($param);	//php5.6以上才要加第二个参数
		$hashedRequestPayload = hash("SHA256", $payload);
		$canonicalRequest = $httpRequestMethod."\n"
			.$canonicalUri."\n"
			.$canonicalQueryString."\n"
			.$canonicalHeaders."\n"
			.$signedHeaders."\n"
			.$hashedRequestPayload;
		// echo $canonicalRequest.PHP_EOL;

		// step 2: build string to sign
		$date = gmdate("Y-m-d", $timestamp);
		$credentialScope = $date."/".$service."/tc3_request";
		$hashedCanonicalRequest = hash("SHA256", $canonicalRequest);
		$stringToSign = $algorithm."\n"
			.$timestamp."\n"
			.$credentialScope."\n"
			.$hashedCanonicalRequest;
		// echo $stringToSign.PHP_EOL;

		// step 3: sign string
		$secretDate = hash_hmac("SHA256", $date, "TC3".$this->secretKey, true);
		$secretService = hash_hmac("SHA256", $service, $secretDate, true);
		$secretSigning = hash_hmac("SHA256", "tc3_request", $secretService, true);
		$signature = hash_hmac("SHA256", $stringToSign, $secretSigning);
		// echo $signature.PHP_EOL;

		// step 4: build authorization
		$authorization = $algorithm
			." Credential=".$this->secretId."/".$credentialScope
			.", SignedHeaders=content-type;host, Signature=".$signature;
		// echo $authorization.PHP_EOL;

		$url = "https://".$host;
		$header[] = "Authorization:".$authorization;
		$header[] = "Content-Type:application/json";
		$header[] = "Host:".$host;
		$header[] = "X-TC-Action:".$action;
		$header[] = "X-TC-Timestamp:".$timestamp;
		$header[] = "X-TC-Version:".$version;
		$header[] = "X-TC-Region:".$region;
		$header[] = "X-TC-Language:zh-CN";
		$res = $this->CurlRequest($url,'post',$payload,$header);
		return $res;
	}

	//发送请求方法
	private function CurlRequest($url,$type = null,$data=null,$header=null)
	{
		//初始化浏览器
		$ch = curl_init();
		//设置浏览器,把参数url传到浏览器的设置当中
		curl_setopt($ch, CURLOPT_URL, $url);
		curl_setopt($ch, CURLOPT_HEADER, false);
		curl_setopt($ch, CURLOPT_NOBODY, false);
		//以字符串形式返回到浏览器当中
		curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
		//禁止https协议验证域名,0就是禁止验证域名且兼容php5.6
		curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0);
		//禁止https协议验证ssl安全认证证书
		curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); 
		//判断data是否有数据,如果有data数据传入那么就把curl的请求方式设置为POST请求方式
		if ( !empty($data) ) {
			switch ($type) {
				case 'get':
					//设置POST请求方式
					@curl_setopt($curl, CURLOPT_HTTPGET, true);
					break;
				case 'post':
					//设置POST请求方式
					@curl_setopt($ch, CURLOPT_POST, true);
					//设置POST的数据包
					@curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
					break;
				case 'put':
					//设置PUT请求方式
					@curl_setopt($ch, CURLOPT_CUSTOMREQUEST,"PUT");
					//设置POST的数据包
					@curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
					break;
				case 'delete':
					//设置POST请求方式
					@curl_setopt ($ch, CURLOPT_CUSTOMREQUEST, "DELETE");
					//设置POST的数据包
					@curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
					break;
				default:
					//设置POST请求方式
					@curl_setopt($ch, CURLOPT_POST, true);
					//设置POST的数据包
					@curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
					break;
			}
		}
		//设置header头
		if ( !empty($header) ) {
			curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
		}
		//让curl发起请求
		$httpCode = curl_exec($ch);
		$errorCode = curl_errno($ch);
		//关闭curl浏览器
		curl_close($ch);
		if(0 !== $errorCode) {
			return false;
		}
		//把请求回来的数据返回
		//return json_decode($httpCode,true); //用output输出,不编码
		return $httpCode;
	}	
}

  下面提供一个简单的API调用示例,如下:

# 获取我在腾讯云注册的域名列表
$rtn = DNSPodDomainDNS::Obj()->DescribeDomainNameList();
print_r($rtn);

# 获取当前域名的所有解析记录
$Domain = "example.com";
$rtn = DNSPodDomainDNS::Obj()->DescribeRecordList($Domain);
print_r($rtn);

  通过这个PHP封装类,我就可以用自己的域名,在自己的家庭网络设备如NAS上实现家里宽带的动态域名解析了,您可以创建一个ddns.php文件,核心代码如下:

//引入前面的类文件
require_once($_SERVER['DOCUMENT_ROOT'].'/DNSPodDomainDNS-inc.php');
#获取当前客户端的ip
$REMOTE_ADDR = $_SERVER['REMOTE_ADDR'];
//IPv4地址更新
if(filter_var($REMOTE_ADDR, FILTER_VALIDATE_IP, FILTER_FLAG_IPV4))
{
	DNSPodDomainDNS::Obj()->ModifyDynamicDNS("@","ddns.example.com",$REMOTE_ADDR,"A");
}

//IPv6地址更新
if(filter_var($REMOTE_ADDR, FILTER_VALIDATE_IP, FILTER_FLAG_IPV6))
{
	DNSPodDomainDNS::Obj()->ModifyDynamicDNS("@","ddns.example.com",$REMOTE_ADDR,"AAAA");
}

  如果您在使用该封装类有任何问题,可留言给我,我会尽快回复。

返回首页    发布日期:2026年06月09日

Copyright © 2026   楚狐在线   All Rights ReservedAZ.   反馈留言