mirror of
https://github.com/mail-in-a-box/mailinabox.git
synced 2024-11-24 02:37:05 +00:00
add a control panel for setting custom dns records so that we dont have to use the api manually
This commit is contained in:
parent
5cf38b950a
commit
90592bb157
@ -172,6 +172,12 @@ def mail_domains():
|
|||||||
|
|
||||||
# DNS
|
# DNS
|
||||||
|
|
||||||
|
@app.route('/dns/zones')
|
||||||
|
@authorized_personnel_only
|
||||||
|
def dns_zones():
|
||||||
|
from dns_update import get_dns_zones
|
||||||
|
return json_response([z[0] for z in get_dns_zones(env)])
|
||||||
|
|
||||||
@app.route('/dns/update', methods=['POST'])
|
@app.route('/dns/update', methods=['POST'])
|
||||||
@authorized_personnel_only
|
@authorized_personnel_only
|
||||||
def dns_update():
|
def dns_update():
|
||||||
@ -196,6 +202,17 @@ def dns_set_secondary_nameserver():
|
|||||||
except ValueError as e:
|
except ValueError as e:
|
||||||
return (str(e), 400)
|
return (str(e), 400)
|
||||||
|
|
||||||
|
@app.route('/dns/set')
|
||||||
|
@authorized_personnel_only
|
||||||
|
def dns_get_records():
|
||||||
|
from dns_update import get_custom_dns_config, get_custom_records
|
||||||
|
additional_records = get_custom_dns_config(env)
|
||||||
|
records = get_custom_records(None, additional_records, env)
|
||||||
|
return json_response([{
|
||||||
|
"qname": r[0],
|
||||||
|
"rtype": r[1],
|
||||||
|
"value": r[2],
|
||||||
|
} for r in records])
|
||||||
|
|
||||||
@app.route('/dns/set/<qname>', methods=['POST'])
|
@app.route('/dns/set/<qname>', methods=['POST'])
|
||||||
@app.route('/dns/set/<qname>/<rtype>', methods=['POST'])
|
@app.route('/dns/set/<qname>/<rtype>', methods=['POST'])
|
||||||
|
@ -254,10 +254,13 @@ def build_zone(domain, all_domains, additional_records, env, is_zone=True):
|
|||||||
def get_custom_records(domain, additional_records, env):
|
def get_custom_records(domain, additional_records, env):
|
||||||
for qname, value in additional_records.items():
|
for qname, value in additional_records.items():
|
||||||
# Is this record for the domain or one of its subdomains?
|
# Is this record for the domain or one of its subdomains?
|
||||||
if qname != domain and not qname.endswith("." + domain): continue
|
# If `domain` is None, return records for all domains.
|
||||||
|
if domain is not None and qname != domain and not qname.endswith("." + domain): continue
|
||||||
|
|
||||||
# Turn the fully qualified domain name in the YAML file into
|
# Turn the fully qualified domain name in the YAML file into
|
||||||
# our short form (None => domain, or a relative QNAME).
|
# our short form (None => domain, or a relative QNAME) if
|
||||||
|
# domain is not None.
|
||||||
|
if domain is not None:
|
||||||
if qname == domain:
|
if qname == domain:
|
||||||
qname = None
|
qname = None
|
||||||
else:
|
else:
|
||||||
|
@ -1,4 +1,7 @@
|
|||||||
<style>
|
<style>
|
||||||
|
#custom-dns-current td.long {
|
||||||
|
word-break: break-all;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
<h2>Custom DNS</h2>
|
<h2>Custom DNS</h2>
|
||||||
@ -7,6 +10,60 @@
|
|||||||
|
|
||||||
<p>It is possible to set custom DNS records on domains hosted here.</p>
|
<p>It is possible to set custom DNS records on domains hosted here.</p>
|
||||||
|
|
||||||
|
<h3>Set Custom DNS Records</h3>
|
||||||
|
|
||||||
|
<p>You can set additional DNS records, such as if you have a website running on another server, to add DKIM records for external mail providers, or for various confirmation-of-ownership tests.</p>
|
||||||
|
|
||||||
|
<form class="form-horizontal" role="form" onsubmit="do_set_custom_dns(); return false;">
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="customdnsQname" class="col-sm-1 control-label">Name</label>
|
||||||
|
<div class="col-sm-10">
|
||||||
|
<table style="max-width: 400px">
|
||||||
|
<tr><td>
|
||||||
|
<input type="text" class="form-control" id="customdnsQname" placeholder="subdomain">
|
||||||
|
</td><td style="padding: 0 1em; font-weight: bold;">.</td><td>
|
||||||
|
<select id="customdnsZone" class="form-control"> </select>
|
||||||
|
</td></tr></table>
|
||||||
|
<div class="text-info" style="margin-top: .5em">Leave the left field blank to set a record on the chosen domain name, or enter a subdomain.</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="customdnsType" class="col-sm-1 control-label">Type</label>
|
||||||
|
<div class="col-sm-10">
|
||||||
|
<select id="customdnsType" class="form-control" style="max-width: 400px" onchange="show_customdns_rtype_hint()">
|
||||||
|
<option value="A" data-hint="Enter an IPv4 address (i.e. a dotted quad, such as 123.456.789.012).">A (IPv4 address)</option>
|
||||||
|
<option value="AAAA" data-hint="Enter an IPv6 address.">AAAA (IPv6 address)</option>
|
||||||
|
<option value="CNAME" data-hint="Enter another domain name followed by a period at the end (e.g. mypage.github.io.).">CNAME (DNS forwarding)</option>
|
||||||
|
<option value="TXT" data-hint="Enter arbitrary text.">TXT (text record)</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="customdnsValue" class="col-sm-1 control-label">Value</label>
|
||||||
|
<div class="col-sm-10">
|
||||||
|
<input type="text" class="form-control" id="customdnsValue" placeholder="">
|
||||||
|
<div id="customdnsTypeHint" class="text-info" style="margin-top: .5em"></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<div class="col-sm-offset-1 col-sm-11">
|
||||||
|
<button type="submit" class="btn btn-primary">Set Record</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
|
||||||
|
<table id="custom-dns-current" class="table" style="width: auto; display: none">
|
||||||
|
<thead>
|
||||||
|
<th>Domain Name</th>
|
||||||
|
<th>Record Type</th>
|
||||||
|
<th>Value</th>
|
||||||
|
<th></th>
|
||||||
|
</thead>
|
||||||
|
<tbody>
|
||||||
|
<tr><td colspan="4">Loading...</td></tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
|
||||||
<h3>Using a Secondary Nameserver</h3>
|
<h3>Using a Secondary Nameserver</h3>
|
||||||
|
|
||||||
<p>If your TLD requires you to have two separate nameservers, you can either set up a secondary (aka “slave”) nameserver or, alternatively, set up <a href="#" onclick="return show_panel('external_dns')">external DNS</a> and ignore the DNS server on this box. If you choose to use a seconday/slave nameserver, you must find a seconday/slave nameserver service provider. Your domain name registrar or virtual cloud provider may provide this service for you. Once you set up the seconday/slave nameserver service, enter the hostname of <em>their</em> secondary nameserver:</p>
|
<p>If your TLD requires you to have two separate nameservers, you can either set up a secondary (aka “slave”) nameserver or, alternatively, set up <a href="#" onclick="return show_panel('external_dns')">external DNS</a> and ignore the DNS server on this box. If you choose to use a seconday/slave nameserver, you must find a seconday/slave nameserver service provider. Your domain name registrar or virtual cloud provider may provide this service for you. Once you set up the seconday/slave nameserver service, enter the hostname of <em>their</em> secondary nameserver:</p>
|
||||||
@ -30,6 +87,7 @@
|
|||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
|
|
||||||
|
|
||||||
<h3>Custom DNS API</h3>
|
<h3>Custom DNS API</h3>
|
||||||
|
|
||||||
<p>Use your box’s DNS API to set custom DNS records on domains hosted here. For instance, you can create your own dynamic DNS service.</p>
|
<p>Use your box’s DNS API to set custom DNS records on domains hosted here. For instance, you can create your own dynamic DNS service.</p>
|
||||||
@ -78,6 +136,52 @@ function show_custom_dns() {
|
|||||||
$('#secondarydnsHostname').val(data.hostname ? data.hostname : '');
|
$('#secondarydnsHostname').val(data.hostname ? data.hostname : '');
|
||||||
$('#secondarydns-clear-instructions').toggle(data.hostname != null);
|
$('#secondarydns-clear-instructions').toggle(data.hostname != null);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
api(
|
||||||
|
"/dns/zones",
|
||||||
|
"GET",
|
||||||
|
{ },
|
||||||
|
function(data) {
|
||||||
|
$('#customdnsZone').text('');
|
||||||
|
for (var i = 0; i < data.length; i++) {
|
||||||
|
$('#customdnsZone').append($('<option/>').text(data[i]));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
show_current_custom_dns();
|
||||||
|
show_customdns_rtype_hint();
|
||||||
|
}
|
||||||
|
|
||||||
|
function show_current_custom_dns() {
|
||||||
|
api(
|
||||||
|
"/dns/set",
|
||||||
|
"GET",
|
||||||
|
{ },
|
||||||
|
function(data) {
|
||||||
|
if (data.length > 0)
|
||||||
|
$('#custom-dns-current').fadeIn();
|
||||||
|
else
|
||||||
|
$('#custom-dns-current').fadeOut();
|
||||||
|
|
||||||
|
$('#custom-dns-current').find("tbody").text('');
|
||||||
|
for (var i = 0; i < data.length; i++) {
|
||||||
|
var tr = $("<tr/>");
|
||||||
|
$('#custom-dns-current').find("tbody").append(tr);
|
||||||
|
tr.attr('data-qname', data[i].qname);
|
||||||
|
tr.attr('data-rtype', data[i].rtype);
|
||||||
|
tr.append($('<td class="long"/>').text(data[i].qname));
|
||||||
|
tr.append($('<td/>').text(data[i].rtype));
|
||||||
|
tr.append($('<td class="long"/>').text(data[i].value));
|
||||||
|
tr.append($('<td>[<a href="#" onclick="return delete_custom_dns_record(this)">delete</a>]</td>'));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function delete_custom_dns_record(elem) {
|
||||||
|
var qname = $(elem).parents('tr').attr('data-qname');
|
||||||
|
var rtype = $(elem).parents('tr').attr('data-rtype');
|
||||||
|
do_set_custom_dns(qname, rtype, "__delete__");
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
function do_set_secondary_dns() {
|
function do_set_secondary_dns() {
|
||||||
@ -96,4 +200,34 @@ function do_set_secondary_dns() {
|
|||||||
show_modal_error("Secondary DNS", $("<pre/>").text(err));
|
show_modal_error("Secondary DNS", $("<pre/>").text(err));
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function do_set_custom_dns(qname, rtype, value) {
|
||||||
|
if (!qname) {
|
||||||
|
if ($('#customdnsQname').val() != '')
|
||||||
|
qname = $('#customdnsQname').val() + '.' + $('#customdnsZone').val();
|
||||||
|
else
|
||||||
|
qname = $('#customdnsZone').val();
|
||||||
|
rtype = $('#customdnsType').val();
|
||||||
|
value = $('#customdnsValue').val();
|
||||||
|
}
|
||||||
|
|
||||||
|
api(
|
||||||
|
"/dns/set/" + qname + "/" + rtype,
|
||||||
|
"POST",
|
||||||
|
{
|
||||||
|
value: value
|
||||||
|
},
|
||||||
|
function(data) {
|
||||||
|
if (data == "") return; // nothing updated
|
||||||
|
show_modal_error("Custom DNS", $("<pre/>").text(data));
|
||||||
|
show_current_custom_dns();
|
||||||
|
},
|
||||||
|
function(err) {
|
||||||
|
show_modal_error("Custom DNS", $("<pre/>").text(err));
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function show_customdns_rtype_hint() {
|
||||||
|
$('#customdnsTypeHint').text($("#customdnsType").find('option:selected').attr('data-hint'));
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
@ -100,7 +100,7 @@
|
|||||||
<li><a href="#ssl" onclick="return show_panel(this);">SSL Certificates</a></li>
|
<li><a href="#ssl" onclick="return show_panel(this);">SSL Certificates</a></li>
|
||||||
<li><a href="#system_backup" onclick="return show_panel(this);">Backup Status</a></li>
|
<li><a href="#system_backup" onclick="return show_panel(this);">Backup Status</a></li>
|
||||||
<li class="divider"></li>
|
<li class="divider"></li>
|
||||||
<li class="dropdown-header">Super Advanced Options</li>
|
<li class="dropdown-header">Advanced Options</li>
|
||||||
<li><a href="#custom_dns" onclick="return show_panel(this);">Custom DNS</a></li>
|
<li><a href="#custom_dns" onclick="return show_panel(this);">Custom DNS</a></li>
|
||||||
<li><a href="#external_dns" onclick="return show_panel(this);">External DNS</a></li>
|
<li><a href="#external_dns" onclick="return show_panel(this);">External DNS</a></li>
|
||||||
</ul>
|
</ul>
|
||||||
|
Loading…
Reference in New Issue
Block a user