| #!/usr/bin/python | |
| import os | |
| import shutil | |
| import shelltoolbox | |
| BASE_PATH = "/etc/opendkim" | |
| BASE_KEY_PATH = os.path.join(BASE_PATH, "keys") | |
| BASE_SELECTOR = "mail" | |
| OPENDKIM_UID = 148 | |
| OPENDKIM_GID = 163 | |
| _generate_key = shelltoolbox.command("/usr/bin/opendkim-genkey") | |
| update_serial = shelltoolbox.command("/etc/bind/update_serial") | |
| reload_opendkim = shelltoolbox.command("/usr/sbin/service", "opendkim", "reload") | |
| def incr(): | |
| file = os.path.join(BASE_KEY_PATH, 'incr') | |
| if os.path.isfile(file): | |
| with open(file) as f: | |
| i = int(f.read().strip()) | |
| else: | |
| i = 5 | |
| i+=1 | |
| with open(file, 'w') as f: | |
| f.write("%d" % i) | |
| return i | |
| def get_domains(): | |
| domains = [] | |
| for file in os.listdir(BASE_KEY_PATH): | |
| if os.path.isdir(os.path.join(BASE_KEY_PATH, file)) and not file.startswith('.'): | |
| domains.append(file) | |
| return domains | |
| def KeyTable(domains, selector): | |
| data = [] | |
| for domain in domains: | |
| data.append( | |
| "%(selector)s._domainkey.%(domain)s %(domain)s:%(selector)s:%(key_path)s/%(domain)s/%(selector)s.private" % { | |
| 'selector': selector, | |
| 'domain': domain, | |
| 'key_path': BASE_KEY_PATH, | |
| } | |
| ) | |
| data.append("") | |
| KeyTable_path = os.path.join(BASE_PATH, "KeyTable") | |
| with open(KeyTable_path + ".new", 'w') as f: | |
| f.write("\n".join(data)) | |
| os.rename(KeyTable_path + ".new", KeyTable_path) | |
| def SigningTable(domains, selector): | |
| data = [] | |
| for domain in domains: | |
| data.append("*@%(domain)s %(selector)s._domainkey.%(domain)s" % {'domain': domain, 'selector': selector}) | |
| data.append("") | |
| SigningTable_path = os.path.join(BASE_PATH, "SigningTable") | |
| with open(SigningTable_path + ".new", 'w') as f: | |
| f.write("\n".join(data)) | |
| os.rename(SigningTable_path + ".new", SigningTable_path) | |
| def TrustedHosts(domains): | |
| data = [ "127.0.0.1", "localhost", "10.0.0.0/8", "192.168.0.0/16", ""] | |
| data.extend(domains) | |
| data.append("") | |
| for domain in domains: | |
| data.append("*.%s" % domain) | |
| data.append("") | |
| TrustedHosts_path = os.path.join(BASE_PATH, "TrustedHosts") | |
| with open(TrustedHosts_path + ".new", 'w') as f: | |
| f.write("\n".join(data)) | |
| os.rename(TrustedHosts_path + ".new", TrustedHosts_path) | |
| def generate_key(domain, selector): | |
| ret = _generate_key('-s', selector, '-d', domain, '-b', "2048") | |
| os.chmod("%s.txt" % selector, 0644) | |
| os.chown("%s.private" % selector, OPENDKIM_UID, OPENDKIM_GID) | |
| return ret | |
| def rotate(domain, i): | |
| dir = os.path.join(BASE_KEY_PATH, domain) | |
| if os.path.isdir(dir): | |
| os.chdir(dir) | |
| try: | |
| os.remove("%s%s.txt" % (BASE_SELECTOR, (i-2))) | |
| os.remove("%s%s.private" % (BASE_SELECTOR, (i-2))) | |
| except OSError: | |
| pass | |
| try: | |
| current_pubkey = os.readlink("current.txt") | |
| except OSError: | |
| generate_key(domain, "%s%s" % (BASE_SELECTOR, (i-1))) | |
| current_pubkey = "%s%s.txt" % (BASE_SELECTOR, (i-1)) | |
| try: | |
| next_pubkey = os.readlink("next.txt") | |
| except OSError: | |
| generate_key(domain, "%s%s" % (BASE_SELECTOR, i)) | |
| next_pubkey = "%s%s.txt" % (BASE_SELECTOR, i) | |
| try: | |
| os.remove("retired.txt") | |
| except OSError: | |
| pass | |
| os.symlink(current_pubkey, "retired.txt") | |
| try: | |
| os.remove("current.txt") | |
| except OSError: | |
| pass | |
| os.symlink(next_pubkey, "current.txt") | |
| try: | |
| os.remove("next.txt") | |
| except OSError: | |
| pass | |
| selector = "%s%s" % (BASE_SELECTOR, (i+1)) | |
| generate_key(domain, selector) | |
| os.symlink("%s.txt" % selector, "next.txt") | |
| print "%s: %s" % (domain, update_serial(domain)) | |
| if __name__ == "__main__": | |
| domains = get_domains() | |
| print "Domains found: %s" % ', '.join(domains) | |
| i = incr() | |
| selector = "%s%s" % (BASE_SELECTOR, i) | |
| for domain in domains: | |
| rotate(domain, i) | |
| KeyTable(domains, selector) | |
| SigningTable(domains, selector) | |
| TrustedHosts(domains) | |
| reload_opendkim() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment