2023-01-14 15:00:44 +05:30
/ *
Technitium DNS Server
2025-02-02 16:03:58 +05:30
Copyright ( C ) 2025 Shreyas Zare ( shreyas @technitium . com )
2023-01-14 15:00:44 +05:30
This program is free software : you can redistribute it and / or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation , either version 3 of the License , or
( at your option ) any later version .
This program is distributed in the hope that it will be useful ,
but WITHOUT ANY WARRANTY ; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
GNU General Public License for more details .
You should have received a copy of the GNU General Public License
along with this program . If not , see < http : //www.gnu.org/licenses/>.
* /
using DnsServerCore.Auth ;
using DnsServerCore.Dns ;
using DnsServerCore.Dns.ResourceRecords ;
using DnsServerCore.Dns.Zones ;
using Microsoft.AspNetCore.Http ;
using System ;
using System.Collections.Generic ;
using System.Net ;
using System.Net.Http ;
2024-03-16 14:01:38 +05:30
using System.Net.Sockets ;
2023-01-14 15:00:44 +05:30
using System.Text.Json ;
2024-09-14 19:31:29 +05:30
using System.Threading ;
2023-01-14 15:00:44 +05:30
using System.Threading.Tasks ;
using TechnitiumLibrary ;
2023-05-27 12:36:57 +05:30
using TechnitiumLibrary.Net ;
2023-01-14 15:00:44 +05:30
using TechnitiumLibrary.Net.Dns ;
using TechnitiumLibrary.Net.Dns.ResourceRecords ;
2023-03-18 13:37:34 +05:30
using TechnitiumLibrary.Net.Http.Client ;
2023-01-14 15:00:44 +05:30
using TechnitiumLibrary.Net.Proxy ;
namespace DnsServerCore
{
2025-02-15 12:51:16 +05:30
public partial class DnsWebService
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
class WebServiceApi
{
#region variables
2024-02-17 18:13:54 +05:30
2025-02-15 12:51:16 +05:30
static readonly char [ ] _domainTrimChars = new char [ ] { '\t' , ' ' , '.' } ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
readonly DnsWebService _dnsWebService ;
readonly Uri _updateCheckUri ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
string _checkForUpdateJsonData ;
DateTime _checkForUpdateJsonDataUpdatedOn ;
const int CHECK_FOR_UPDATE_JSON_DATA_CACHE_TIME_SECONDS = 3600 ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
#endregion
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
#region constructor
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
public WebServiceApi ( DnsWebService dnsWebService , Uri updateCheckUri )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
_dnsWebService = dnsWebService ;
_updateCheckUri = updateCheckUri ;
2023-01-14 15:00:44 +05:30
}
2025-02-15 12:51:16 +05:30
#endregion
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
#region private
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
private async Task < string > GetCheckForUpdateJsonData ( )
{
if ( ( _checkForUpdateJsonData is null ) | | ( DateTime . UtcNow > _checkForUpdateJsonDataUpdatedOn . AddSeconds ( CHECK_FOR_UPDATE_JSON_DATA_CACHE_TIME_SECONDS ) ) )
{
SocketsHttpHandler handler = new SocketsHttpHandler ( ) ;
handler . Proxy = _dnsWebService . _dnsServer . Proxy ;
handler . UseProxy = _dnsWebService . _dnsServer . Proxy is not null ;
handler . AutomaticDecompression = DecompressionMethods . All ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
using ( HttpClient http = new HttpClient ( new HttpClientNetworkHandler ( handler , _dnsWebService . _dnsServer . PreferIPv6 ? HttpClientNetworkType . PreferIPv6 : HttpClientNetworkType . Default , _dnsWebService . _dnsServer ) ) )
{
_checkForUpdateJsonData = await http . GetStringAsync ( _updateCheckUri ) ;
_checkForUpdateJsonDataUpdatedOn = DateTime . UtcNow ;
}
}
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
return _checkForUpdateJsonData ;
2023-01-14 15:00:44 +05:30
}
2025-02-15 12:51:16 +05:30
#endregion
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
#region public
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
public async Task CheckForUpdateAsync ( HttpContext context )
{
Utf8JsonWriter jsonWriter = context . GetCurrentJsonWriter ( ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( _updateCheckUri is null )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
jsonWriter . WriteBoolean ( "updateAvailable" , false ) ;
return ;
2023-01-14 15:00:44 +05:30
}
2025-02-15 12:51:16 +05:30
try
{
string jsonData = await GetCheckForUpdateJsonData ( ) ;
using JsonDocument jsonDocument = JsonDocument . Parse ( jsonData ) ;
JsonElement jsonResponse = jsonDocument . RootElement ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
string updateVersion = jsonResponse . GetProperty ( "updateVersion" ) . GetString ( ) ;
string updateTitle = jsonResponse . GetPropertyValue ( "updateTitle" , null ) ;
string updateMessage = jsonResponse . GetPropertyValue ( "updateMessage" , null ) ;
string downloadLink = jsonResponse . GetPropertyValue ( "downloadLink" , null ) ;
string instructionsLink = jsonResponse . GetPropertyValue ( "instructionsLink" , null ) ;
string changeLogLink = jsonResponse . GetPropertyValue ( "changeLogLink" , null ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
bool updateAvailable = new Version ( updateVersion ) > _dnsWebService . _currentVersion ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
jsonWriter . WriteBoolean ( "updateAvailable" , updateAvailable ) ;
jsonWriter . WriteString ( "updateVersion" , updateVersion ) ;
jsonWriter . WriteString ( "currentVersion" , _dnsWebService . GetServerVersion ( ) ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( updateAvailable )
{
jsonWriter . WriteString ( "updateTitle" , updateTitle ) ;
jsonWriter . WriteString ( "updateMessage" , updateMessage ) ;
jsonWriter . WriteString ( "downloadLink" , downloadLink ) ;
jsonWriter . WriteString ( "instructionsLink" , instructionsLink ) ;
jsonWriter . WriteString ( "changeLogLink" , changeLogLink ) ;
}
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
string strLog = "Check for update was done {updateAvailable: " + updateAvailable + "; updateVersion: " + updateVersion + ";" ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( ! string . IsNullOrEmpty ( updateTitle ) )
strLog + = " updateTitle: " + updateTitle + ";" ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( ! string . IsNullOrEmpty ( updateMessage ) )
strLog + = " updateMessage: " + updateMessage + ";" ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( ! string . IsNullOrEmpty ( downloadLink ) )
strLog + = " downloadLink: " + downloadLink + ";" ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( ! string . IsNullOrEmpty ( instructionsLink ) )
strLog + = " instructionsLink: " + instructionsLink + ";" ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( ! string . IsNullOrEmpty ( changeLogLink ) )
strLog + = " changeLogLink: " + changeLogLink + ";" ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
strLog + = "}" ;
2024-03-16 14:01:38 +05:30
2025-02-15 12:51:16 +05:30
_dnsWebService . _log . Write ( context . GetRemoteEndPoint ( _dnsWebService . _webServiceRealIpHeader ) , strLog ) ;
}
catch ( Exception ex )
2024-03-16 14:01:38 +05:30
{
2025-02-15 12:51:16 +05:30
_dnsWebService . _log . Write ( context . GetRemoteEndPoint ( _dnsWebService . _webServiceRealIpHeader ) , "Check for update was done {updateAvailable: False;}\r\n" + ex . ToString ( ) ) ;
2024-03-16 14:01:38 +05:30
2025-02-15 12:51:16 +05:30
jsonWriter . WriteBoolean ( "updateAvailable" , false ) ;
2024-03-16 14:01:38 +05:30
}
}
2025-02-15 12:51:16 +05:30
public async Task ResolveQueryAsync ( HttpContext context )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
UserSession session = context . GetCurrentSession ( ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( ! _dnsWebService . _authManager . IsPermitted ( PermissionSection . DnsClient , session . User , PermissionFlag . View ) )
throw new DnsWebServiceException ( "Access was denied." ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
HttpRequest request = context . Request ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
string server = request . GetQueryOrForm ( "server" ) ;
string domain = request . GetQueryOrForm ( "domain" ) . Trim ( _domainTrimChars ) ;
DnsResourceRecordType type = request . GetQueryOrFormEnum < DnsResourceRecordType > ( "type" ) ;
DnsTransportProtocol protocol = request . GetQueryOrFormEnum ( "protocol" , DnsTransportProtocol . Udp ) ;
bool dnssecValidation = request . GetQueryOrForm ( "dnssec" , bool . Parse , false ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
NetworkAddress eDnsClientSubnet = request . GetQueryOrForm ( "eDnsClientSubnet" , NetworkAddress . Parse , null ) ;
if ( eDnsClientSubnet is not null )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
switch ( eDnsClientSubnet . AddressFamily )
2024-09-14 19:31:29 +05:30
{
2025-02-15 12:51:16 +05:30
case AddressFamily . InterNetwork :
if ( eDnsClientSubnet . PrefixLength = = 32 )
eDnsClientSubnet = new NetworkAddress ( eDnsClientSubnet . Address , 24 ) ;
2025-02-02 16:03:58 +05:30
2025-02-15 12:51:16 +05:30
break ;
2023-08-12 13:15:29 +05:30
2025-02-15 12:51:16 +05:30
case AddressFamily . InterNetworkV6 :
if ( eDnsClientSubnet . PrefixLength = = 128 )
eDnsClientSubnet = new NetworkAddress ( eDnsClientSubnet . Address , 56 ) ;
2023-08-12 13:15:29 +05:30
2025-02-15 12:51:16 +05:30
break ;
}
2023-08-12 13:15:29 +05:30
}
2025-02-02 16:03:58 +05:30
2025-02-15 12:51:16 +05:30
bool importResponse = request . GetQueryOrForm ( "import" , bool . Parse , false ) ;
NetProxy proxy = _dnsWebService . _dnsServer . Proxy ;
bool preferIPv6 = _dnsWebService . _dnsServer . PreferIPv6 ;
ushort udpPayloadSize = _dnsWebService . _dnsServer . UdpPayloadSize ;
bool randomizeName = false ;
bool qnameMinimization = _dnsWebService . _dnsServer . QnameMinimization ;
const int RETRIES = 1 ;
const int TIMEOUT = 10000 ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
DnsDatagram dnsResponse ;
List < DnsDatagram > rawResponses = new List < DnsDatagram > ( ) ;
string dnssecErrorMessage = null ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( server . Equals ( "recursive-resolver" , StringComparison . OrdinalIgnoreCase ) )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
if ( type = = DnsResourceRecordType . AXFR )
throw new DnsServerException ( "Cannot do zone transfer (AXFR) for 'recursive-resolver'." ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
DnsQuestionRecord question ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( ( type = = DnsResourceRecordType . PTR ) & & IPAddress . TryParse ( domain , out IPAddress address ) )
question = new DnsQuestionRecord ( address , DnsClass . IN ) ;
else
question = new DnsQuestionRecord ( domain , type , DnsClass . IN ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
DnsCache dnsCache = new DnsCache ( ) ;
dnsCache . MinimumRecordTtl = 0 ;
dnsCache . MaximumRecordTtl = 7 * 24 * 60 * 60 ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
try
{
dnsResponse = await TechnitiumLibrary . TaskExtensions . TimeoutAsync ( async delegate ( CancellationToken cancellationToken1 )
{
return await DnsClient . RecursiveResolveAsync ( question , dnsCache , proxy , preferIPv6 , udpPayloadSize , randomizeName , qnameMinimization , dnssecValidation , eDnsClientSubnet , RETRIES , TIMEOUT , rawResponses : rawResponses , cancellationToken : cancellationToken1 ) ;
} , DnsServer . RECURSIVE_RESOLUTION_TIMEOUT ) ;
}
catch ( DnsClientResponseDnssecValidationException ex )
{
if ( ex . InnerException is DnsClientResponseDnssecValidationException ex1 )
ex = ex1 ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
dnsResponse = ex . Response ;
dnssecErrorMessage = ex . Message ;
importResponse = false ;
}
}
else if ( server . Equals ( "system-dns" , StringComparison . OrdinalIgnoreCase ) )
{
DnsClient dnsClient = new DnsClient ( ) ;
dnsClient . Proxy = proxy ;
dnsClient . PreferIPv6 = preferIPv6 ;
dnsClient . RandomizeName = randomizeName ;
dnsClient . Retries = RETRIES ;
dnsClient . Timeout = TIMEOUT ;
dnsClient . UdpPayloadSize = udpPayloadSize ;
dnsClient . DnssecValidation = dnssecValidation ;
dnsClient . EDnsClientSubnet = eDnsClientSubnet ;
try
{
dnsResponse = await dnsClient . ResolveAsync ( domain , type ) ;
2023-01-14 15:00:44 +05:30
}
2025-02-15 12:51:16 +05:30
catch ( DnsClientResponseDnssecValidationException ex )
{
if ( ex . InnerException is DnsClientResponseDnssecValidationException ex1 )
ex = ex1 ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
dnsResponse = ex . Response ;
dnssecErrorMessage = ex . Message ;
importResponse = false ;
}
2023-01-14 15:00:44 +05:30
}
else
{
2025-02-15 12:51:16 +05:30
if ( ( type = = DnsResourceRecordType . AXFR ) & & ( protocol = = DnsTransportProtocol . Udp ) )
protocol = DnsTransportProtocol . Tcp ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
NameServerAddress nameServer ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( server . Equals ( "this-server" , StringComparison . OrdinalIgnoreCase ) )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
switch ( protocol )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
case DnsTransportProtocol . Udp :
nameServer = _dnsWebService . _dnsServer . ThisServer ;
break ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
case DnsTransportProtocol . Tcp :
nameServer = _dnsWebService . _dnsServer . ThisServer . ChangeProtocol ( DnsTransportProtocol . Tcp ) ;
break ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
case DnsTransportProtocol . Tls :
throw new DnsServerException ( "Cannot use DNS-over-TLS protocol for 'this-server'. Please use the TLS certificate domain name as the server." ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
case DnsTransportProtocol . Https :
throw new DnsServerException ( "Cannot use DNS-over-HTTPS protocol for 'this-server'. Please use the TLS certificate domain name with a url as the server." ) ;
2023-05-27 12:36:57 +05:30
2025-02-15 12:51:16 +05:30
case DnsTransportProtocol . Quic :
throw new DnsServerException ( "Cannot use DNS-over-QUIC protocol for 'this-server'. Please use the TLS certificate domain name as the server." ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
default :
throw new NotSupportedException ( "DNS transport protocol is not supported: " + protocol . ToString ( ) ) ;
}
2025-02-02 16:03:58 +05:30
2025-02-15 12:51:16 +05:30
proxy = null ; //no proxy required for this server
}
else
{
nameServer = NameServerAddress . Parse ( server ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( nameServer . Protocol ! = protocol )
nameServer = nameServer . ChangeProtocol ( protocol ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( nameServer . IsIPEndPointStale )
await nameServer . ResolveIPAddressAsync ( _dnsWebService . _dnsServer , _dnsWebService . _dnsServer . PreferIPv6 ) ;
2023-09-23 18:12:41 +05:30
2025-02-15 12:51:16 +05:30
if ( ( nameServer . DomainEndPoint is null ) & & ( ( protocol = = DnsTransportProtocol . Udp ) | | ( protocol = = DnsTransportProtocol . Tcp ) ) )
2023-09-23 18:12:41 +05:30
{
2025-02-15 12:51:16 +05:30
try
{
await nameServer . ResolveDomainNameAsync ( _dnsWebService . _dnsServer ) ;
}
catch
{ }
2023-09-23 18:12:41 +05:30
}
}
2025-02-15 12:51:16 +05:30
DnsClient dnsClient = new DnsClient ( nameServer ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
dnsClient . Proxy = proxy ;
dnsClient . PreferIPv6 = preferIPv6 ;
dnsClient . RandomizeName = randomizeName ;
dnsClient . Retries = RETRIES ;
dnsClient . Timeout = TIMEOUT ;
dnsClient . UdpPayloadSize = udpPayloadSize ;
dnsClient . DnssecValidation = dnssecValidation ;
dnsClient . EDnsClientSubnet = eDnsClientSubnet ;
if ( dnssecValidation )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
if ( ( type = = DnsResourceRecordType . PTR ) & & IPAddress . TryParse ( domain , out IPAddress ptrIp ) )
domain = ptrIp . GetReverseDomain ( ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
//load trust anchors into dns client if domain is locally hosted
_dnsWebService . _dnsServer . AuthZoneManager . LoadTrustAnchorsTo ( dnsClient , domain , type ) ;
}
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
try
{
dnsResponse = await dnsClient . ResolveAsync ( domain , type ) ;
}
catch ( DnsClientResponseDnssecValidationException ex )
{
if ( ex . InnerException is DnsClientResponseDnssecValidationException ex1 )
ex = ex1 ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
dnsResponse = ex . Response ;
dnssecErrorMessage = ex . Message ;
importResponse = false ;
2023-01-14 15:00:44 +05:30
}
2025-02-15 12:51:16 +05:30
if ( type = = DnsResourceRecordType . AXFR )
dnsResponse = dnsResponse . Join ( ) ;
2023-01-14 15:00:44 +05:30
}
2025-02-15 12:51:16 +05:30
if ( importResponse )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
bool isZoneImport = false ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( type = = DnsResourceRecordType . AXFR )
{
isZoneImport = true ;
}
else
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
foreach ( DnsResourceRecord record in dnsResponse . Answer )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
if ( record . Type = = DnsResourceRecordType . SOA )
{
if ( record . Name . Equals ( domain , StringComparison . OrdinalIgnoreCase ) )
isZoneImport = true ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
break ;
}
2023-01-14 15:00:44 +05:30
}
}
2025-02-15 12:51:16 +05:30
AuthZoneInfo zoneInfo = _dnsWebService . _dnsServer . AuthZoneManager . FindAuthZoneInfo ( domain ) ;
if ( ( zoneInfo is null ) | | ( ( zoneInfo . Type ! = AuthZoneType . Primary ) & & ! zoneInfo . Name . Equals ( domain , StringComparison . OrdinalIgnoreCase ) ) | | ( isZoneImport & & ! zoneInfo . Name . Equals ( domain , StringComparison . OrdinalIgnoreCase ) ) )
{
if ( ! _dnsWebService . _authManager . IsPermitted ( PermissionSection . Zones , session . User , PermissionFlag . Modify ) )
throw new DnsWebServiceException ( "Access was denied." ) ;
zoneInfo = _dnsWebService . _dnsServer . AuthZoneManager . CreatePrimaryZone ( domain ) ;
if ( zoneInfo is null )
throw new DnsServerException ( "Cannot import records: failed to create primary zone." ) ;
//set permissions
_dnsWebService . _authManager . SetPermission ( PermissionSection . Zones , zoneInfo . Name , session . User , PermissionFlag . ViewModifyDelete ) ;
_dnsWebService . _authManager . SetPermission ( PermissionSection . Zones , zoneInfo . Name , _dnsWebService . _authManager . GetGroup ( Group . ADMINISTRATORS ) , PermissionFlag . ViewModifyDelete ) ;
_dnsWebService . _authManager . SetPermission ( PermissionSection . Zones , zoneInfo . Name , _dnsWebService . _authManager . GetGroup ( Group . DNS_ADMINISTRATORS ) , PermissionFlag . ViewModifyDelete ) ;
_dnsWebService . _authManager . SaveConfigFile ( ) ;
}
else
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
if ( ! _dnsWebService . _authManager . IsPermitted ( PermissionSection . Zones , zoneInfo . Name , session . User , PermissionFlag . Modify ) )
throw new DnsWebServiceException ( "Access was denied." ) ;
switch ( zoneInfo . Type )
2023-01-14 15:00:44 +05:30
{
2025-02-15 12:51:16 +05:30
case AuthZoneType . Primary :
break ;
case AuthZoneType . Forwarder :
if ( type = = DnsResourceRecordType . AXFR )
throw new DnsServerException ( "Cannot import records via zone transfer: import zone must be of primary type." ) ;
break ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
default :
throw new DnsServerException ( "Cannot import records: import zone must be of primary or forwarder type." ) ;
2023-01-14 15:00:44 +05:30
}
}
2025-02-15 12:51:16 +05:30
if ( type = = DnsResourceRecordType . AXFR )
{
_dnsWebService . _dnsServer . AuthZoneManager . SyncZoneTransferRecords ( zoneInfo . Name , dnsResponse . Answer ) ;
}
else
{
List < DnsResourceRecord > importRecords = new List < DnsResourceRecord > ( dnsResponse . Answer . Count + dnsResponse . Authority . Count ) ;
foreach ( DnsResourceRecord record in dnsResponse . Answer )
{
if ( record . Name . Equals ( zoneInfo . Name , StringComparison . OrdinalIgnoreCase ) | | record . Name . EndsWith ( "." + zoneInfo . Name , StringComparison . OrdinalIgnoreCase ) | | ( zoneInfo . Name . Length = = 0 ) )
{
record . RemoveExpiry ( ) ;
2025-04-19 15:52:43 +05:30
record . Tag = null ; //remove cache zone record info
2025-02-15 12:51:16 +05:30
importRecords . Add ( record ) ;
if ( record . Type = = DnsResourceRecordType . NS )
record . SyncGlueRecords ( dnsResponse . Additional ) ;
}
}
foreach ( DnsResourceRecord record in dnsResponse . Authority )
{
if ( record . Name . Equals ( zoneInfo . Name , StringComparison . OrdinalIgnoreCase ) | | record . Name . EndsWith ( "." + zoneInfo . Name , StringComparison . OrdinalIgnoreCase ) | | ( zoneInfo . Name . Length = = 0 ) )
{
record . RemoveExpiry ( ) ;
2025-04-19 15:52:43 +05:30
record . Tag = null ; //remove cache zone record info
2025-02-15 12:51:16 +05:30
importRecords . Add ( record ) ;
if ( record . Type = = DnsResourceRecordType . NS )
record . SyncGlueRecords ( dnsResponse . Additional ) ;
}
}
_dnsWebService . _dnsServer . AuthZoneManager . ImportRecords ( zoneInfo . Name , importRecords , true , true ) ;
}
_dnsWebService . _log . Write ( context . GetRemoteEndPoint ( _dnsWebService . _webServiceRealIpHeader ) , "[" + session . User . Username + "] DNS Client imported record(s) for authoritative zone {server: " + server + "; zone: " + zoneInfo . DisplayName + "; type: " + type + ";}" ) ;
2023-01-14 15:00:44 +05:30
}
2025-02-15 12:51:16 +05:30
Utf8JsonWriter jsonWriter = context . GetCurrentJsonWriter ( ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
if ( dnssecErrorMessage is not null )
jsonWriter . WriteString ( "warningMessage" , dnssecErrorMessage ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
jsonWriter . WritePropertyName ( "result" ) ;
dnsResponse . SerializeTo ( jsonWriter ) ;
2023-01-14 15:00:44 +05:30
2025-02-15 12:51:16 +05:30
jsonWriter . WritePropertyName ( "rawResponses" ) ;
jsonWriter . WriteStartArray ( ) ;
2024-03-16 14:01:38 +05:30
2025-02-15 12:51:16 +05:30
for ( int i = 0 ; i < rawResponses . Count ; i + + )
rawResponses [ i ] . SerializeTo ( jsonWriter ) ;
2024-03-16 14:01:38 +05:30
2025-02-15 12:51:16 +05:30
jsonWriter . WriteEndArray ( ) ;
}
2024-03-16 14:01:38 +05:30
2025-02-15 12:51:16 +05:30
#endregion
2023-01-14 15:00:44 +05:30
}
}
}