]> git.ipfire.org Git - thirdparty/pdns.git/commitdiff
API: Auth: honor rectify settings on create zone 12087/head
authorChris Hofstaedtler <chris.hofstaedtler@deduktiva.com>
Wed, 12 Oct 2022 13:45:50 +0000 (15:45 +0200)
committerChris Hofstaedtler <chris.hofstaedtler@deduktiva.com>
Wed, 12 Oct 2022 14:38:41 +0000 (16:38 +0200)
pdns/ws-auth.cc
regression-tests.api/test_Zones.py

index 7cd51079a1b8fc850ab24ab33e27299d2e327197..7eafc5bbf768d984338ed65c7e3247114143e211 100644 (file)
@@ -657,7 +657,7 @@ static void extractDomainInfoFromDocument(const Json& document, boost::optional<
 }
 
 // Must be called within backend transaction.
-static void updateDomainSettingsFromDocument(UeberBackend& B, const DomainInfo& di, const DNSName& zonename, const Json& document) {
+static void updateDomainSettingsFromDocument(UeberBackend& B, const DomainInfo& di, const DNSName& zonename, const Json& document, bool zoneWasModified) {
   boost::optional<DomainInfo::DomainKind> kind;
   boost::optional<vector<ComboAddress>> masters;
   boost::optional<DNSName> catalog;
@@ -692,7 +692,7 @@ static void updateDomainSettingsFromDocument(UeberBackend& B, const DomainInfo&
 
 
   DNSSECKeeper dk(&B);
-  bool shouldRectify = false;
+  bool shouldRectify = zoneWasModified;
   bool dnssecInJSON = false;
   bool dnssecDocVal = false;
   bool nsec3paramInJSON = false;
@@ -1708,15 +1708,6 @@ static void apiServerZones(HttpRequest* req, HttpResponse* resp) {
     if (!nameservers.is_null() && !nameservers.is_array() && zonekind != DomainInfo::Slave)
       throw ApiException("Nameservers is not a list");
 
-    string soa_edit_api_kind;
-    if (document["soa_edit_api"].is_string()) {
-      soa_edit_api_kind = document["soa_edit_api"].string_value();
-    }
-    else {
-      soa_edit_api_kind = "DEFAULT";
-    }
-    string soa_edit_kind = document["soa_edit"].string_value();
-
     // if records/comments are given, load and check them
     bool have_soa = false;
     bool have_zone_ns = false;
@@ -1752,7 +1743,6 @@ static void apiServerZones(HttpRequest* req, HttpResponse* resp) {
 
       if (rr.qtype.getCode() == QType::SOA && rr.qname==zonename) {
         have_soa = true;
-        increaseSOARecord(rr, soa_edit_api_kind, soa_edit_kind);
       }
       if (rr.qtype.getCode() == QType::NS && rr.qname==zonename) {
         have_zone_ns = true;
@@ -1774,7 +1764,7 @@ static void apiServerZones(HttpRequest* req, HttpResponse* resp) {
       sd.serial=document["serial"].int_value();
       autorr.qtype = QType::SOA;
       autorr.content = makeSOAContent(sd)->getZoneRepresentation(true);
-      increaseSOARecord(autorr, soa_edit_api_kind, soa_edit_kind);
+      // updateDomainSettingsFromDocument will apply SOA-EDIT-API as needed
       new_records.push_back(autorr);
     }
 
@@ -1827,10 +1817,8 @@ static void apiServerZones(HttpRequest* req, HttpResponse* resp) {
 
     di.backend->startTransaction(zonename, di.id);
 
-    // updateDomainSettingsFromDocument does NOT fill out the default we've established above.
-    if (!soa_edit_api_kind.empty()) {
-      di.backend->setDomainMetadataOne(zonename, "SOA-EDIT-API", soa_edit_api_kind);
-    }
+    // will be overridden by updateDomainSettingsFromDocument, if given in document.
+    di.backend->setDomainMetadataOne(zonename, "SOA-EDIT-API", "DEFAULT");
 
     for(auto rr : new_records) {
       rr.domain_id = di.id;
@@ -1841,7 +1829,7 @@ static void apiServerZones(HttpRequest* req, HttpResponse* resp) {
       di.backend->feedComment(c);
     }
 
-    updateDomainSettingsFromDocument(B, di, zonename, document);
+    updateDomainSettingsFromDocument(B, di, zonename, document, !new_records.empty());
 
     di.backend->commitTransaction();
 
@@ -1908,7 +1896,7 @@ static void apiServerZoneDetail(HttpRequest* req, HttpResponse* resp) {
     // update domain settings
 
     di.backend->startTransaction(zonename, -1);
-    updateDomainSettingsFromDocument(B, di, zonename, req->json());
+    updateDomainSettingsFromDocument(B, di, zonename, req->json(), false);
     di.backend->commitTransaction();
 
     resp->body = "";
index 15384539b95a2508c627656cf4942effe9f987bb..a36415fac24e81f5d2c070ef68feed9412cf55a5 100644 (file)
@@ -6,7 +6,7 @@ import unittest
 from copy import deepcopy
 from parameterized import parameterized
 from pprint import pprint
-from test_helper import ApiTestCase, unique_zone_name, is_auth, is_auth_lmdb, is_recursor, get_db_records, pdnsutil_rectify
+from test_helper import ApiTestCase, unique_zone_name, is_auth, is_auth_lmdb, is_recursor, get_db_records, pdnsutil_rectify, sdig
 
 
 def get_rrset(data, qname, qtype):
@@ -591,10 +591,9 @@ class AuthZones(ApiTestCase, AuthZonesHelperMixin):
 
     def test_create_zone_dnssec_serial(self):
         """
-        Create a zone set/unset "dnssec" and see if the serial was increased
+        Create a zone, then set and unset "dnssec", then check if the serial was increased
         after every step
         """
-        name = unique_zone_name()
         name, payload, data = self.create_zone()
 
         soa_serial = get_first_rec(data, name, 'SOA')['content'].split(' ')[2]
@@ -2077,9 +2076,8 @@ $ORIGIN %NAME%
         self.assertEqual(len(r.json()), 5)
 
     @unittest.skipIf(is_auth_lmdb(), "No get_db_records for LMDB")
-    def test_default_api_rectify(self):
+    def test_default_api_rectify_dnssec(self):
         name = unique_zone_name()
-        search = name.split('.')[0]
         rrsets = [
             {
                 "name": 'a.' + name,
@@ -2104,6 +2102,35 @@ $ORIGIN %NAME%
         dbrecs = get_db_records(name, 'AAAA')
         self.assertIsNotNone(dbrecs[0]['ordername'])
 
+    def test_default_api_rectify_nodnssec(self):
+        """Without any DNSSEC settings, rectify should still add ENTs. Setup the zone
+        so ENTs are necessary, and check for their existence using sdig.
+        """
+        name = unique_zone_name()
+        rrsets = [
+            {
+                "name": 'a.sub.' + name,
+                "type": "AAAA",
+                "ttl": 3600,
+                "records": [{
+                    "content": "2001:DB8::1",
+                    "disabled": False,
+                }],
+            },
+            {
+                "name": 'b.sub.' + name,
+                "type": "AAAA",
+                "ttl": 3600,
+                "records": [{
+                    "content": "2001:DB8::2",
+                    "disabled": False,
+                }],
+            },
+        ]
+        self.create_zone(name=name, rrsets=rrsets)
+        # default-api-rectify is yes (by default). expect rectify to have happened.
+        assert 'Rcode: 0 ' in sdig('sub.' + name, 'TXT')
+
     @unittest.skipIf(is_auth_lmdb(), "No get_db_records for LMDB")
     def test_override_api_rectify(self):
         name = unique_zone_name()