Joe Clarke 1 éve
szülő
commit
8944e7795c
1 módosított fájl, 71 hozzáadás és 100 törlés
  1. 71 100
      automation/services/dns-hook.py

+ 71 - 100
automation/services/dns-hook.py

@@ -29,18 +29,15 @@ import sys
 import json
 from sparker import Sparker, MessageType  # type: ignore
 import re
-import requests
-from requests.packages.urllib3.exceptions import InsecureRequestWarning  # type: ignore
-
-requests.packages.urllib3.disable_warnings(InsecureRequestWarning)
 import traceback
 import logging
+from elemental_utils import ElementalDns
+from elemental_utils import cpnr
+from elemental_utils.cpnr.query import RequestError
+import os
 import CLEUCreds  # type: ignore
 from cleu.config import Config as C  # type: ignore
 
-CNR_HEADERS = {"Accept": "application/json", "Content-Type": "application/json"}
-CNR_AUTH = (CLEUCreds.CPNR_USERNAME, CLEUCreds.CPNR_PASSWORD)
-
 ALLOWED_TO_CREATE = [
     "jclarke@cisco.com",
     "anjesani@cisco.com",
@@ -56,110 +53,82 @@ spark = Sparker(token=CLEUCreds.SPARK_TOKEN, logit=True)
 SPARK_ROOM = "DNS Queries"
 
 
-def check_for_alias(alias):
-    global CNR_HEADERS, CNR_AUTH
-
-    url = C.DNS_BASE + "/CCMRRSet" + "/{}".format(alias)
-
-    response = requests.request("GET", url, params={"zoneOrigin": C.DNS_DOMAIN}, auth=CNR_AUTH, headers=CNR_HEADERS, verify=False)
-    if response.status_code == 404:
-        return None
-
-    res = {}
-    j = response.json()
-
-    hostname = ""
-
-    for rr in j["rrs"]["stringItem"]:
-        m = re.search(r"^IN CNAME (.+)", rr)
-        if m:
-            hostname = m.group(1)
-            break
-
-    res["hostname"] = hostname
-
-    return res
-
-
-def create_alias(hostname, alias):
-    global CNR_HEADERS, CNR_AUTH
-
-    url = C.DNS_BASE + "/CCMRRSet" + "/{}".format(alias)
-
-    if re.search(r"\.", hostname) and not hostname.endswith("."):
-        hostname += "."
-
-    if not hostname.endswith("."):
-        hostname += "." + C.DNS_DOMAIN + "."
-
-    rr_obj = {"name": alias, "zoneOrigin": C.DNS_DOMAIN, "rrs": {"stringItem": ["IN CNAME {}".format(hostname)]}}
-
-    response = requests.request("PUT", url, headers=CNR_HEADERS, auth=CNR_AUTH, json=rr_obj, verify=False)
-    response.raise_for_status()
+def check_for_alias(edns: ElementalDns, alias: str) -> cpnr.models.model.Record:
+    rrset = edns.rrset.get(alias, zoneOrigin=C.DNS_DOMAIN + ".")
+    if rrset:
+        for rr in rrset.rrList["CCMRRItem"]:
+            if rr["rrType"] == "CNAME":
+                return rrset
 
+    return None
 
-def delete_alias(alias):
-    global CNR_HEADERS, CNR_AUTH
 
-    url = C.DNS_BASE + "/CCMRRSet" + "/{}".format(alias)
+def create_alias(edns: ElementalDns, hostname: str, alias: str):
+    cpnr_record = {}
 
-    response = requests.request("DELETE", url, params={"zoneOrigin": C.DNS_DOMAIN}, auth=CNR_AUTH, headers=CNR_HEADERS, verify=False)
-    response.raise_for_status()
+    cpnr_record["name"] = alias
+    cpnr_record["zoneOrigin"] = C.DNS_DOMAIN + "."
+    target = f"{hostname}.{C.DNS_DOMAIN}."
+    cpnr_record["rrList"] = {"CCMRRItem": [{"rdata": target, "rrClass": "IN", "rrType": "CNAME"}]}
 
+    edns.rrset.add(**cpnr_record)
 
-def delete_record(hostname):
-    global CNR_HEADERS
 
-    url = C.DNS_BASE + "/CCMHost" + "/{}".format(hostname)
-    rrurl = C.DNS_BASE + "/CCMRRSet" + "/{}".format(hostname)
+def delete_alias(alias: cpnr.models.model.Record) -> None:
+    alias.delete()
 
-    response = requests.request("DELETE", url, params={"zoneOrigin": C.DNS_DOMAIN}, headers=CNR_HEADERS, verify=False)
-    response.raise_for_status()
-
-    response = requests.request("DELETE", rrurl, params={"zoneOrigin": C.DNS_DOMAIN}, headers=CNR_HEADERS, verify=False)
-
-
-def check_for_record(hostname):
-    global CNR_HEADERS, CNR_AUTH
-
-    url = C.DNS_BASE + "/CCMHost" + "/{}".format(hostname)
-
-    response = requests.request("GET", url, params={"zoneOrigin": C.DNS_DOMAIN}, auth=CNR_AUTH, headers=CNR_HEADERS, verify=False)
-    if response.status_code == 404:
-        return None
-
-    res = {}
-    j = response.json()
-
-    res["ip"] = j["addrs"]["stringItem"][0]
-
-    return res
-
-
-def create_record(hostname, ip, aliases, message_from):
-    global CNR_HEADERS, CNR_AUTH
-
-    url = C.DNS_BASE + "/CCMHost" + "/{}".format(hostname)
-    host_obj = {"addrs": {"stringItem": [ip]}, "name": hostname, "zoneOrigin": C.DNS_DOMAIN}
 
+def delete_record(edns: ElementalDns, record: cpnr.models.model.Record) -> None:
+    name = record.name
+    rrset = edns.rrset.get(name, zoneOrigin=C.DNS_DOMAIN + ".")
+    try:
+        record.delete()
+    except RequestError as e:
+        if e.req.status_code != 404:
+            # We may end up deleting the same record twice.
+            # If it's already gone, don't complain.
+            raise
+
+    if rrset:
+        try:
+            rrset.delete()
+        except RequestError as e:
+            if e.req.status_code != 404:
+                # We may end up deleting the same record twice.
+                # If it's already gone, don't complain.
+                raise
+
+
+def check_for_record(edns: ElementalDns, hostname: str) -> cpnr.models.model.Record:
+    return edns.host.get(hostname, zoneOrigin=C.DNS_DOMAIN + ".")
+
+
+def create_record(edns: ElementalDns, hostname: str, ip: str, aliases: list, message_from: str) -> None:
+    cpnr_record = {}
+
+    cpnr_record["name"] = hostname
+    cpnr_record["addrs"] = {"stringItem": [ip]}
+    cpnr_record["zoneOrigin"] = C.DNS_DOMAIN + "."
+    cpnr_record["createPtrRecords"] = True
     if aliases is not None:
         aliases = re.sub(r"\s+", "", aliases)
         alist = aliases.split(",")
 
         alist = [x + "." + C.DNS_DOMAIN + "." if not x.endswith(".") else x for x in alist]
-        host_obj["aliases"] = {"stringItem": alist}
+        cpnr_record["aliases"] = {"stringItem": alist}
 
-    response = requests.request("PUT", url, headers=CNR_HEADERS, auth=CNR_AUTH, json=host_obj, verify=False)
-    response.raise_for_status()
+    txt_record = f'IN TXT "v=_static created by: {message_from}'
 
-    rr_obj = {"name": hostname, "zoneOrigin": C.DNS_DOMAIN, "rrs": {"stringItem": [f'IN TXT "v=_static created by: {message_from}']}}
-    rrurl = C.DNS_BASE + "/CCMRRSet" + "/{}".format(hostname)
-
-    response = requests.request("PUT", rrurl, headers=CNR_HEADERS, auth=CNR_AUTH, json=rr_obj, verify=False)
-    response.raise_for_status()
+    edns.host.add(**cpnr_record)
+    rrs = edns.rrset.get(hostname, zoneOrigin=C.DNS_DOMAIN + ".")
+    rrs.rrList["CCMRRItem"].append({"rdata": txt_record, "rrClass": "IN", "rrType": "TXT"})
+    rrs.save()
 
 
 if __name__ == "__main__":
+    os.environ["CPNR_USERNAME"] = CLEUCreds.CPNR_USERNAME
+    os.environ["CPNR_PASSWORD"] = CLEUCreds.CPNR_PASSWORD
+
     print("Content-type: application/json\r\n\r\n")
 
     output = sys.stdin.read()
@@ -206,6 +175,8 @@ if __name__ == "__main__":
     txt = msg["text"]
     found_hit = False
 
+    edns = ElementalDns()
+
     if re.search(r"\bhelp\b", txt, re.I):
         spark.post_to_spark(
             C.WEBEX_TEAM,
@@ -222,12 +193,12 @@ if __name__ == "__main__":
             if message_from not in ALLOWED_TO_CREATE:
                 spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "I'm sorry, {}.  I can't do that for you.".format(message_from))
             else:
-                res = check_for_alias(m.group(3))
+                res = check_for_alias(edns, m.group(3))
                 if res is None:
                     spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "I didn't find an alias {}".format(m.group(3)))
                 else:
                     try:
-                        delete_alias(m.group(3))
+                        delete_alias(res)
                         spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "Alias {} deleted successfully.".format(m.group(3)), MessageType.GOOD)
                     except Exception as e:
                         spark.post_to_spark(
@@ -241,12 +212,12 @@ if __name__ == "__main__":
             if message_from not in ALLOWED_TO_CREATE:
                 spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "I'm sorry, {}.  I can't do that for you.".format(message_from))
             else:
-                res = check_for_record(m.group(2))
+                res = check_for_record(edns, m.group(2))
                 if res is None:
                     spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "I didn't find a DNS record for {}.".format(m.group(2)))
                 else:
                     try:
-                        delete_record(m.group(2))
+                        delete_record(edns, res)
                         spark.post_to_spark(
                             C.WEBEX_TEAM, SPARK_ROOM, "DNS record for {} deleted successfully.".format(m.group(2)), MessageType.GOOD
                         )
@@ -265,13 +236,13 @@ if __name__ == "__main__":
             if message_from not in ALLOWED_TO_CREATE:
                 spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "I'm sorry, {}.  I can't do that for you.".format(message_from))
             else:
-                res = check_for_record(m.group(2))
+                res = check_for_record(edns, m.group(2))
                 if res is not None:
                     spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "_{}_ is already in DNS as **{}**".format(m.group(2), res["ip"]))
                 else:
                     hostname = re.sub(r"\.{}".format(C.DNS_DOMAIN), "", m.group(2))
                     try:
-                        create_record(m.group(2), m.group(3), m.group(8), message_from)
+                        create_record(edns, m.group(2), m.group(3), m.group(8), message_from)
                         spark.post_to_spark(
                             C.WEBEX_TEAM, SPARK_ROOM, "Successfully created record for {}.".format(m.group(2)), MessageType.GOOD
                         )
@@ -291,7 +262,7 @@ if __name__ == "__main__":
                 alist = aliases.split(",")
                 already_exists = False
                 for alias in alist:
-                    res = check_for_alias(alias)
+                    res = check_for_alias(edns, alias)
                     if res is not None:
                         already_exists = True
                         spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "_{}_ is already an alias for **{}**".format(alias, res["hostname"]))
@@ -304,7 +275,7 @@ if __name__ == "__main__":
                     success = True
                     for alias in alist:
                         try:
-                            create_alias(m.group(8), alias)
+                            create_alias(edns, m.group(8), alias)
                         except Exception as e:
                             spark.post_to_spark(C.WEBEX_TEAM, SPARK_ROOM, "Failed to create alias {}: {}".format(alias, e), MessageType.BAD)
                             success = False