| name | inwx-dns |
| description | Manage INWX domains and DNS records via the domrobot XML-RPC API. Use when the user wants to create, update, delete, or query DNS records, transfer domains, register domains, manage contacts, handle DNSSEC, manage certificates, check domain availability or pricing, set up DynDNS, or check account/billing status at INWX. Triggers on "inwx", "dns record", "domain transfer", "nameserver", "dns zone", "wildcard record", "domain status", "domain registration", "dnssec", "dyndns", "ssl certificate". |
| version | 1.0.0 |
INWX API — Complete Reference
Prerequisites
pip3 install --user --break-system-packages inwx-domrobot 2>/dev/null || pip3 install inwx-domrobot
Authentication
from INWX.Domrobot import ApiClient
api = ApiClient(api_url=ApiClient.API_LIVE_URL)
api.login('username', 'password')
api.login('username', 'password', tfa_token='123456')
api.login('username', 'password', shared_secret='BASE32SECRET')
Important: 2FA codes expire in 30 seconds. Execute login and all API calls in a single script.
Credentials: Always ask the user. Never store in code. Reuse from conversation if previously provided.
Test environment: Use ApiClient.API_OTE_URL instead of API_LIVE_URL.
Account API
api.call_api('account.login', {'user': 'username', 'pass': 'password'})
api.call_api('account.unlock', {'tan': '123456'})
api.call_api('account.logout', {})
api.call_api('account.info', {})
api.call_api('account.list', {})
api.call_api('account.create', {
'user': 'subuser', 'pass': 'password', 'email': 'sub@example.com',
'firstname': 'John', 'lastname': 'Doe',
})
api.call_api('account.update', {'email': 'new@example.com'})
api.call_api('account.changepassword', {'oldpass': 'old', 'newpass': 'new'})
api.call_api('account.delete', {'user': 'subuser'})
api.call_api('account.check', {'user': 'testuser'})
api.call_api('account.addrole', {'user': 'subuser', 'role': 'DOMAIN_ADMIN'})
api.call_api('account.removerole', {'user': 'subuser', 'role': 'DOMAIN_ADMIN'})
api.call_api('account.getroles', {'user': 'subuser'})
Accounting API
api.call_api('accounting.accountBalance', {})
api.call_api('accounting.log', {})
api.call_api('accounting.creditLogById', {'id': 12345})
api.call_api('accounting.lockedFunds', {})
api.call_api('accounting.getInvoice', {'invoiceId': 12345})
api.call_api('accounting.listInvoices', {})
api.call_api('accounting.getPreviewInvoice', {})
api.call_api('accounting.getReceipt', {'receiptId': 12345})
api.call_api('accounting.getstatement', {'from': '2024-01-01', 'to': '2024-12-31'})
api.call_api('accounting.refund', {'transactionId': 12345})
Domain API
Registration & Lifecycle
res = api.call_api('domain.check', {'domain': 'example.com'})
res = api.call_api('domain.check', {'domain': ['example.com', 'example.de', 'example.app']})
api.call_api('domain.create', {
'domain': 'example.com',
'period': '1Y',
'ns': ['ns.inwx.de', 'ns2.inwx.de', 'ns3.inwx.eu'],
'registrant': CONTACT_ID,
'admin': CONTACT_ID,
'tech': CONTACT_ID,
'billing': CONTACT_ID,
})
api.call_api('domain.renew', {'domain': 'example.com', 'period': '1Y'})
api.call_api('domain.delete', {'domain': 'example.com'})
api.call_api('domain.restore', {'domain': 'example.com'})
Transfer
api.call_api('domain.transfer', {
'domain': 'example.com',
'authCode': 'AUTH-CODE',
'ns': ['ns.inwx.de', 'ns2.inwx.de', 'ns3.inwx.eu'],
'registrant': CONTACT_ID,
'admin': CONTACT_ID,
'tech': CONTACT_ID,
'billing': CONTACT_ID,
})
api.call_api('domain.transfercancel', {'domain': 'example.com'})
api.call_api('domain.transferOut', {'domain': 'example.com'})
api.call_api('domain.push', {'domain': 'example.com', 'target': 'other-user'})
Transfer notes:
.de domains: tech and billing contacts must be PERSON type (not ORG)
clientTransferProhibited: transfer lock must be removed at current registrar
- Transfer costs one year of registration (extends expiry by one year)
.de transfers are near-instant; gTLDs (.com, .app) take up to 5 days
Domain Info & Management
res = api.call_api('domain.info', {'domain': 'example.com'})
res = api.call_api('domain.list', {})
api.call_api('domain.update', {
'domain': 'example.com',
'renewalMode': 'AUTOEXPIRE',
'ns': ['ns.inwx.de', 'ns2.inwx.de', 'ns3.inwx.eu'],
'transferLock': True,
})
api.call_api('domain.trade', {
'domain': 'example.com',
'registrant': NEW_CONTACT_ID,
})
api.call_api('domain.whois', {'domain': 'example.com'})
api.call_api('domain.log', {'domain': 'example.com'})
api.call_api('domain.stats', {})
api.call_api('domain.setClientHold', {'domain': 'example.com'})
api.call_api('domain.removeClientHold', {'domain': 'example.com'})
Pricing
api.call_api('domain.getdomainprice', {'domain': 'example.com'})
api.call_api('domain.getalldomainprices', {})
api.call_api('domain.getRules', {'tld': 'com'})
api.call_api('domain.priceChanges', {})
api.call_api('domain.getPromos', {})
api.call_api('domain.getTldGroups', {})
api.call_api('domain.getextradatarules', {'tld': 'de'})
Nameserver (DNS) API
Zone Management
api.call_api('nameserver.create', {
'domain': 'example.com',
'type': 'MASTER',
'ns': ['ns.inwx.de', 'ns2.inwx.de', 'ns3.inwx.eu'],
})
res = api.call_api('nameserver.info', {'domain': 'example.com'})
for r in res['resData']['record']:
print(r['id'], r['type'], r['name'], r['content'], r['ttl'])
res = api.call_api('nameserver.list', {})
api.call_api('nameserver.update', {
'domain': 'example.com',
'type': 'MASTER',
})
api.call_api('nameserver.delete', {'domain': 'example.com'})
api.call_api('nameserver.check', {'domain': 'example.com'})
api.call_api('nameserver.export', {'domain': 'example.com'})
api.call_api('nameserver.import', {
'domain': 'example.com',
'content': '$ORIGIN example.com.\n@ IN A 1.2.3.4',
})
Record Management
api.call_api('nameserver.createRecord', {
'domain': 'example.com',
'type': 'A',
'name': 'www',
'content': '1.2.3.4',
'ttl': 300,
})
api.call_api('nameserver.createRecord', {
'domain': 'example.com',
'type': 'MX',
'name': '@',
'content': 'mx1.example.com',
'ttl': 3600,
'prio': 10,
})
api.call_api('nameserver.createRecord', {
'domain': 'example.com',
'type': 'SRV',
'name': '_sip._tcp',
'content': '0 5060 sip.example.com',
'ttl': 3600,
'prio': 10,
})
api.call_api('nameserver.createRecord', {
'domain': 'example.com',
'type': 'CAA',
'name': '@',
'content': '0 issue "letsencrypt.org"',
'ttl': 3600,
})
api.call_api('nameserver.createRecord', {
'domain': 'example.com',
'type': 'URL',
'name': '@',
'content': 'https://target.com',
'ttl': 300,
'urlRedirectType': 'HEADER301',
})
api.call_api('nameserver.updateRecord', {
'id': RECORD_ID,
'content': '5.6.7.8',
'ttl': 600,
})
api.call_api('nameserver.deleteRecord', {'id': RECORD_ID})
Bulk Record Operations
res = api.call_api('nameserver.info', {'domain': 'example.com'})
for r in res['resData']['record']:
if r['type'] == 'A' and '*.app' in r['name']:
api.call_api('nameserver.deleteRecord', {'id': r['id']})
Nameserver Set API
api.call_api('nameserverset.create', {
'name': 'default-ns',
'ns': ['ns.inwx.de', 'ns2.inwx.de', 'ns3.inwx.eu'],
})
api.call_api('nameserverset.list', {})
api.call_api('nameserverset.info', {'id': SET_ID})
api.call_api('nameserverset.update', {'id': SET_ID, 'ns': ['ns.inwx.de', 'ns2.inwx.de']})
api.call_api('nameserverset.delete', {'id': SET_ID})
Contact API
res = api.call_api('contact.list', {})
for c in res['resData']['contact']:
print(c['id'], c['type'], c['name'], c.get('org'), c['email'])
api.call_api('contact.info', {'id': CONTACT_ID})
api.call_api('contact.create', {
'type': 'PERSON',
'name': 'John Doe',
'street': 'Main St 1',
'city': 'Berlin',
'pc': '10115',
'cc': 'DE',
'voice': '+49.301234567',
'email': 'john@example.com',
})
api.call_api('contact.create', {
'type': 'ORG',
'name': 'John Doe',
'org': 'ACME Corp',
'street': 'Main St 1',
'city': 'Berlin',
'pc': '10115',
'cc': 'DE',
'voice': '+49.301234567',
'email': 'info@acme.com',
})
api.call_api('contact.update', {'id': CONTACT_ID, 'email': 'new@example.com'})
api.call_api('contact.delete', {'id': CONTACT_ID})
api.call_api('contact.check', {'id': CONTACT_ID})
DNSSEC API
api.call_api('dnssec.list', {'domain': 'example.com'})
api.call_api('dnssec.info', {'id': KEY_ID})
api.call_api('dnssec.create', {
'domain': 'example.com',
'flags': 257,
'protocol': 3,
'algorithm': 13,
'publicKey': 'BASE64KEY...',
})
api.call_api('dnssec.update', {'id': KEY_ID, 'publicKey': 'NEWBASE64KEY...'})
api.call_api('dnssec.delete', {'id': KEY_ID})
api.call_api('dnssec.sign', {'domain': 'example.com'})
api.call_api('dnssec.unsign', {'domain': 'example.com'})
DynDNS API
api.call_api('dyndns.create', {
'domain': 'example.com',
'name': 'home',
'type': 'A',
'content': '1.2.3.4',
'user': 'dynuser',
'pass': 'dynpass',
})
api.call_api('dyndns.list', {})
api.call_api('dyndns.info', {'id': DYNDNS_ID})
api.call_api('dyndns.update', {'id': DYNDNS_ID, 'content': '5.6.7.8'})
api.call_api('dyndns.delete', {'id': DYNDNS_ID})
api.call_api('dyndns.enable', {'id': DYNDNS_ID})
api.call_api('dyndns.disable', {'id': DYNDNS_ID})
DynDNS update URL: https://dyndns.inwx.com/nic/update?myip=NEW_IP
Certificate (SSL/TLS) API
api.call_api('certificate.list', {})
api.call_api('certificate.info', {'id': CERT_ID})
api.call_api('certificate.create', {
'product': 'COMODO_POSITIVE_SSL',
'csr': '-----BEGIN CERTIFICATE REQUEST-----...',
'period': '1Y',
'approverEmail': 'admin@example.com',
})
api.call_api('certificate.renew', {'id': CERT_ID, 'period': '1Y'})
api.call_api('certificate.delete', {'id': CERT_ID})
api.call_api('certificate.reissue', {'id': CERT_ID, 'csr': '...'})
api.call_api('certificate.resendApproverEmail', {'id': CERT_ID})
api.call_api('certificate.getProducts', {})
Hosting API
api.call_api('hosting.list', {})
api.call_api('hosting.info', {'id': HOSTING_ID})
api.call_api('hosting.create', {
'product': 'HOSTING_BASIC',
'domain': 'example.com',
})
api.call_api('hosting.update', {'id': HOSTING_ID, 'product': 'HOSTING_PRO'})
api.call_api('hosting.delete', {'id': HOSTING_ID})
Message API
api.call_api('message.list', {})
api.call_api('message.update', {'id': MSG_ID, 'read': True})
Wildcard DNS Records
INWX supports wildcard records. * matches all subdomains at that level:
*.example.com matches foo.example.com but NOT bar.foo.example.com
*.sub.example.com matches foo.sub.example.com
For multi-level wildcards (e.g., Kubernetes environments):
wildcards = ['*.app', '*.dev.app', '*.test.app', '*.prod.app']
for name in wildcards:
api.call_api('nameserver.createRecord', {
'domain': 'example.com',
'type': 'A',
'name': name,
'content': INGRESS_IP,
'ttl': 300,
})
Response Codes
| Code | Meaning |
|---|
| 1000 | Success |
| 1001 | Success, action pending |
| 2001 | Internal server error |
| 2002 | Command use error (e.g., invalid 2FA) |
| 2003 | Required parameter missing |
| 2004 | Parameter value range error |
| 2005 | Parameter value syntax error |
| 2104 | Billing failure (insufficient credit) |
| 2200 | Authentication error |
| 2201 | Authorization error |
| 2302 | Object already exists |
| 2303 | Object does not exist |
| 2304 | Object status prohibits operation |
| 2306 | Parameter value policy error |
Best Practices
- Always logout after API calls:
api.logout()
- Batch operations in a single login session to minimize 2FA prompts
- Check response codes before reporting success
- Use INWX nameservers:
ns.inwx.de, ns2.inwx.de, ns3.inwx.eu
- Activate delegation after domain transfer via
domain.update with NS records
- Prefer wildcards over individual A records when subdomains share the same target
- Handle billing failures by informing the user to top up their INWX credit
- .de domains require PERSON contacts for tech and billing (not ORG)