commit 0f77ac174b4ed4caabb4a9cb58db0653e0907807 Author: Christian Date: Tue Apr 28 21:55:16 2026 +0200 list und add gehen diff --git a/hosting.kdbx b/hosting.kdbx new file mode 100644 index 0000000..3345118 Binary files /dev/null and b/hosting.kdbx differ diff --git a/inwx_add_record.py b/inwx_add_record.py new file mode 100644 index 0000000..9c88037 --- /dev/null +++ b/inwx_add_record.py @@ -0,0 +1,104 @@ +#!/usr/bin/env python3 +import sys +import os +import subprocess + +# Import-Fix für die Library-Struktur +try: + from INWX.Domrobot import ApiClient +except ImportError: + from inwx.Domrobot import ApiClient + +# --- KONFIGURATION --- +API_URL = 'https://api.domrobot.com' +BASE_DIR = os.path.dirname(os.path.abspath(__file__)) +KP_DB_PATH = os.path.join(BASE_DIR, "hosting.kdbx") +KP_ENTRY_NAME = "inwx" + +# Daten für den neuen Record +DOMAIN = "ma151.de" +NEW_NAME = "srv1" # Subdomain +NEW_TYPE = "A" # Record-Typ +NEW_VALUE = "167.86.90.246" +NEW_TTL = 3600 # Time to Live in Sekunden + +def get_creds(): + """Liest User/Passwort sicher aus KeePassXC.""" + try: + cmd = ["keepassxc-cli", "show", "-s", KP_DB_PATH, KP_ENTRY_NAME] + output = subprocess.check_output(cmd, text=True) + creds = {} + for line in output.splitlines(): + if ":" in line: + k, v = line.split(":", 1) + creds[k.strip().lower()] = v.strip() + return creds.get("username") or creds.get("benutzername"), creds.get("password") or creds.get("passwort") + except Exception as e: + print(f"❌ KeePass-Fehler: {e}") + return None, None + +def main(): + user, password = get_creds() + if not user or not password: + sys.exit(1) + + api = ApiClient(api_url=API_URL) + + # 1. Login + login_res = api.login(user, password) + if login_res['code'] != 1000: + print(f"❌ Login fehlgeschlagen: {login_res['msg']}") + sys.exit(1) + + print(f"✅ Login erfolgreich. Prüfe Record: {NEW_NAME}.{DOMAIN} ({NEW_TYPE} -> {NEW_VALUE})") + + # 2. Prüfen, ob der Record bereits existiert + # Wir rufen alle Records der Domain ab + info_res = api.call_api('nameserver.info', {'domain': DOMAIN}) + + if info_res['code'] != 1000: + print(f"❌ Fehler beim Abrufen der Domain-Info: {info_res['msg']}") + api.logout() + sys.exit(1) + + records = info_res['resData'].get('record', []) + + # Den FQDN (Full Qualified Domain Name) zusammenbauen, wie INWX ihn speichert + full_name = f"{NEW_NAME}.{DOMAIN}" + + # Suche nach Dubletten + already_exists = False + for rec in records: + # INWX gibt Namen oft mit oder ohne Punkt am Ende zurück, wir prüfen beides + rec_name = rec['name'].rstrip('.') + if (rec_name == full_name and + rec['type'] == NEW_TYPE and + rec['content'] == NEW_VALUE): + already_exists = True + break + + if already_exists: + print(f"ℹ️ Record existiert bereits exakt so. Keine Änderung nötig.") + else: + print(f"🚀 Record nicht gefunden. Erstelle {full_name}...") + + # 3. Record erstellen + create_params = { + 'domain': DOMAIN, + 'name': NEW_NAME, + 'type': NEW_TYPE, + 'content': NEW_VALUE, + 'ttl': NEW_TTL + } + + create_res = api.call_api('nameserver.createRecord', create_params) + + if create_res['code'] == 1000: + print(f"✅ Erfolg! Record wurde mit ID {create_res['resData']['id']} angelegt.") + else: + print(f"❌ Fehler beim Erstellen: {create_res['msg']} (Code: {create_res['code']})") + + api.logout() + +if __name__ == "__main__": + main() diff --git a/inwx_list.py b/inwx_list.py new file mode 100644 index 0000000..0686d3e --- /dev/null +++ b/inwx_list.py @@ -0,0 +1,78 @@ +#!/usr/bin/env python3 +import sys +import os +import subprocess + +# Import-Fix für Linux/Mac +try: + from INWX.Domrobot import ApiClient +except ImportError: + from inwx.Domrobot import ApiClient + +# --- KONFIGURATION --- +API_URL = 'https://api.domrobot.com' +BASE_DIR = os.path.dirname(os.path.abspath(__file__)) +KP_DB_PATH = os.path.join(BASE_DIR, "hosting.kdbx") +KP_ENTRY_NAME = "inwx" +DOMAIN = "ma151.de" + +def get_creds(): + """Holt die echten Daten (inkl. Passwort) aus KeePassXC.""" + try: + # -s sorgt dafür, dass das Passwort nicht als 'PROTECTED' ausgegeben wird + cmd = ["keepassxc-cli", "show", "-s", KP_DB_PATH, KP_ENTRY_NAME] + output = subprocess.check_output(cmd, text=True) + + creds = {} + for line in output.splitlines(): + if ":" in line: + k, v = line.split(":", 1) + creds[k.strip().lower()] = v.strip() + + user = creds.get("username") or creds.get("benutzername") or creds.get("user") + password = creds.get("password") or creds.get("passwort") + + return user, password + except Exception as e: + print(f"❌ KeePass-Fehler: {e}") + return None, None + +def main(): + user, password = get_creds() + if not user or not password: + sys.exit(1) + + # ApiClient mit der korrekten URL (Library fügt /xmlrpc/ an) + api = ApiClient(api_url=API_URL) + + print(f"Versuche Login für: {user}") + + # Login + login_res = api.login(user, password) + + if login_res['code'] == 1000: + print("✅ Login erfolgreich!") + print(f"Rufe Records für {DOMAIN} ab...") + + try: + # Deine Library-Version nutzt laut DEBUG 'call_api' + res = api.call_api('nameserver.info', {'domain': DOMAIN}) + + if res['code'] == 1000: + records = res['resData']['record'] + print(f"\n{'TYP':<8} {'NAME':<35} {'WERT'}") + print("-" * 75) + for rec in records: + print(f"{rec['type']:<8} {rec['name']:<35} {rec['content']}") + else: + print(f"❌ API Fehler: {res['msg']} (Code: {res['code']})") + + except Exception as e: + print(f"❌ Fehler beim Abruf mit call_api: {e}") + + api.logout() + else: + print(f"❌ Login fehlgeschlagen: {login_res['msg']} (Code: {login_res['code']})") + +if __name__ == "__main__": + main()